| @@ -1,7 +1,12 @@ | |||
| package dag | |||
| import ( | |||
| "fmt" | |||
| "reflect" | |||
| "strings" | |||
| "gitlink.org.cn/cloudream/common/utils/lo2" | |||
| "gitlink.org.cn/cloudream/common/utils/reflect2" | |||
| ) | |||
| type Graph struct { | |||
| @@ -55,6 +60,100 @@ func (g *Graph) NewValueVar() *ValueVar { | |||
| return &ValueVar{} | |||
| } | |||
| func (g *Graph) Dump() string { | |||
| nodeIDs := make(map[Node]int) | |||
| for i, node := range g.Nodes { | |||
| nodeIDs[node] = i | |||
| } | |||
| var sb strings.Builder | |||
| for _, node := range g.Nodes { | |||
| id, ok := nodeIDs[node] | |||
| if !ok { | |||
| id = len(nodeIDs) | |||
| nodeIDs[node] = id | |||
| } | |||
| sb.WriteString(fmt.Sprintf("[%v]%v\n", id, nodeTypeName(node))) | |||
| if node.InputStreams().Len() > 0 { | |||
| sb.WriteString("SIn: ") | |||
| for i, in := range node.InputStreams().Slots { | |||
| if i > 0 { | |||
| sb.WriteString(", ") | |||
| } | |||
| if in == nil { | |||
| sb.WriteString("?") | |||
| } else { | |||
| sb.WriteString(fmt.Sprintf("%v", nodeIDs[in.Src])) | |||
| } | |||
| } | |||
| sb.WriteString("\n") | |||
| } | |||
| if node.OutputStreams().Len() > 0 { | |||
| sb.WriteString("SOut: ") | |||
| for i, out := range node.OutputStreams().Slots { | |||
| if i > 0 { | |||
| sb.WriteString(", ") | |||
| } | |||
| sb.WriteString("(") | |||
| for i2, dst := range out.Dst { | |||
| if i2 > 0 { | |||
| sb.WriteString(", ") | |||
| } | |||
| sb.WriteString(fmt.Sprintf("%v", nodeIDs[dst])) | |||
| } | |||
| sb.WriteString(")") | |||
| } | |||
| sb.WriteString("\n") | |||
| } | |||
| if node.InputValues().Len() > 0 { | |||
| sb.WriteString("VIn: ") | |||
| for i, in := range node.InputValues().Slots { | |||
| if i > 0 { | |||
| sb.WriteString(", ") | |||
| } | |||
| if in == nil { | |||
| sb.WriteString("?") | |||
| } else { | |||
| sb.WriteString(fmt.Sprintf("%v", nodeIDs[in.Src])) | |||
| } | |||
| } | |||
| sb.WriteString("\n") | |||
| } | |||
| if node.OutputValues().Len() > 0 { | |||
| sb.WriteString("VOut: ") | |||
| for i, out := range node.OutputValues().Slots { | |||
| if i > 0 { | |||
| sb.WriteString(", ") | |||
| } | |||
| sb.WriteString("(") | |||
| for i2, dst := range out.Dst { | |||
| if i2 > 0 { | |||
| sb.WriteString(", ") | |||
| } | |||
| sb.WriteString(fmt.Sprintf("%v", nodeIDs[dst])) | |||
| } | |||
| sb.WriteString(")") | |||
| } | |||
| sb.WriteString("\n") | |||
| } | |||
| } | |||
| return sb.String() | |||
| } | |||
| func nodeTypeName(node Node) string { | |||
| typ := reflect2.TypeOfValue(node) | |||
| for typ.Kind() == reflect.Ptr { | |||
| typ = typ.Elem() | |||
| } | |||
| return typ.Name() | |||
| } | |||
| func AddNode[N Node](graph *Graph, typ N) N { | |||
| graph.AddNode(typ) | |||
| return typ | |||