init
This commit is contained in:
commit
671f259cb6
102
main.go
Normal file
102
main.go
Normal file
|
@ -0,0 +1,102 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bufio"
|
||||||
|
"fmt"
|
||||||
|
"os"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Node struct {
|
||||||
|
Name string
|
||||||
|
Children []*Node
|
||||||
|
}
|
||||||
|
|
||||||
|
func ParseTree(s string) *Node {
|
||||||
|
// Split string into name and children parts
|
||||||
|
var name string
|
||||||
|
var childrenStr string
|
||||||
|
if idx := strings.Index(s, "<"); idx >= 0 {
|
||||||
|
if idx+1 < len(s)-1 {
|
||||||
|
name = strings.TrimSpace(s[:idx])
|
||||||
|
childrenStr = s[idx+1 : len(s)-1]
|
||||||
|
} else {
|
||||||
|
name = strings.TrimSpace(s[:len(s)-2])
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
name = strings.TrimSpace(s)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Create new node
|
||||||
|
node := &Node{Name: name}
|
||||||
|
|
||||||
|
// Parse children
|
||||||
|
if childrenStr != "" {
|
||||||
|
b := 0
|
||||||
|
last_child := 0
|
||||||
|
for i, symb := range childrenStr {
|
||||||
|
if symb == '<' {
|
||||||
|
b += 1
|
||||||
|
} else if symb == '>' {
|
||||||
|
b -= 1
|
||||||
|
if b == 0 {
|
||||||
|
childNode := ParseTree(childrenStr[last_child : i+1])
|
||||||
|
node.Children = append(node.Children, childNode)
|
||||||
|
last_child = i + 2
|
||||||
|
}
|
||||||
|
} else if symb == ',' && b == 0 {
|
||||||
|
if last_child < i {
|
||||||
|
childNode := ParseTree(childrenStr[last_child:i])
|
||||||
|
node.Children = append(node.Children, childNode)
|
||||||
|
last_child = i + 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if last_child < len(childrenStr) {
|
||||||
|
childNode := ParseTree(childrenStr[last_child:])
|
||||||
|
node.Children = append(node.Children, childNode)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return node
|
||||||
|
}
|
||||||
|
|
||||||
|
func ToGraphviz(node *Node) string {
|
||||||
|
var sb strings.Builder
|
||||||
|
sb.WriteString("digraph {\n")
|
||||||
|
|
||||||
|
// Recursive function to add nodes and edges to string builder
|
||||||
|
var traverse func(n *Node)
|
||||||
|
traverse = func(n *Node) {
|
||||||
|
// Add node to Graphviz string
|
||||||
|
sb.WriteString(fmt.Sprintf(" \"%p\" [label=%s];\n", n, strconv.Quote(n.Name)))
|
||||||
|
|
||||||
|
// Traverse children and add edges
|
||||||
|
for _, child := range n.Children {
|
||||||
|
sb.WriteString(fmt.Sprintf(" \"%p\" -> \"%p\";\n", n, child))
|
||||||
|
traverse(child)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
traverse(node)
|
||||||
|
sb.WriteString("}")
|
||||||
|
|
||||||
|
return sb.String()
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
// Read all data from stdin
|
||||||
|
scanner := bufio.NewScanner(os.Stdin)
|
||||||
|
var typeStr string
|
||||||
|
for scanner.Scan() {
|
||||||
|
typeStr += scanner.Text() + "\n"
|
||||||
|
}
|
||||||
|
|
||||||
|
// Apply the formatter function to the input string
|
||||||
|
root := ParseTree(typeStr)
|
||||||
|
graph := ToGraphviz(root)
|
||||||
|
|
||||||
|
// Print the result
|
||||||
|
fmt.Println(graph)
|
||||||
|
}
|
Loading…
Reference in a new issue