Working on it more. :(
This commit is contained in:
parent
5c8e8cba21
commit
dc34a45b94
BIN
go/pov/cmd/cmd
BIN
go/pov/cmd/cmd
Binary file not shown.
@ -1,13 +1,26 @@
|
|||||||
package main
|
package main
|
||||||
|
|
||||||
import pov ".."
|
import (
|
||||||
|
"fmt"
|
||||||
|
|
||||||
|
pov ".."
|
||||||
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
g := pov.New()
|
g := pov.New()
|
||||||
g.AddNode("sibling")
|
|
||||||
g.AddNode("x")
|
|
||||||
g.AddNode("parent")
|
g.AddNode("parent")
|
||||||
g.AddArc("parent", "sibling")
|
|
||||||
g.AddArc("parent", "x")
|
g.AddArc("parent", "x")
|
||||||
|
g.AddArc("x", "sib-2")
|
||||||
|
g.AddArc("x", "sib-3")
|
||||||
|
g.AddArc("x", "sib-4")
|
||||||
|
g.AddArc("parent", "sibling")
|
||||||
|
g.AddArc("sibling", "child-1")
|
||||||
|
g.AddArc("sibling", "child-2")
|
||||||
|
g.AddArc("sibling", "child-3")
|
||||||
|
g.AddArc("child-3", "grandchild-1")
|
||||||
|
g.AddArc("grandchild-1", "greatgrandchild-1")
|
||||||
pov.PrintGraph(g)
|
pov.PrintGraph(g)
|
||||||
|
fmt.Println("== Change Root to child-3 ==")
|
||||||
|
n := g.ChangeRoot("parent", "child-3")
|
||||||
|
pov.PrintGraph(n)
|
||||||
}
|
}
|
||||||
|
174
go/pov/pov.go
174
go/pov/pov.go
@ -7,128 +7,128 @@ type Graph struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func New() *Graph {
|
func New() *Graph {
|
||||||
g := new(Graph)
|
return new(Graph)
|
||||||
return g
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// GetNode returns the node from the graph with label lbl
|
|
||||||
func (g *Graph) GetNode(lbl string) *Node {
|
|
||||||
for i := range g.leaves {
|
|
||||||
if n := g.leaves[i].GetNode(lbl); n != nil {
|
|
||||||
return n
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// AddNode adds a top level leaf with label lbl
|
|
||||||
func (g *Graph) AddNode(lbl string) {
|
func (g *Graph) AddNode(lbl string) {
|
||||||
|
// Make sure that g doesn't already have node lbl
|
||||||
|
if g.getNode(lbl) != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
g.leaves = append(g.leaves, Node{label: lbl})
|
g.leaves = append(g.leaves, Node{label: lbl})
|
||||||
}
|
}
|
||||||
|
|
||||||
// addRealNode adds the node n to the top level
|
func (g *Graph) AddArc(fr, to string) {
|
||||||
func (g *Graph) addRealNode(n *Node) {
|
if frN := g.getNode(fr); frN != nil {
|
||||||
g.leaves = append(g.leaves, *n)
|
frN.AddNode(to)
|
||||||
}
|
|
||||||
|
|
||||||
// AddArc creates a new node after to named from
|
|
||||||
func (g *Graph) AddArc(from, to string) {
|
|
||||||
if n := g.GetNode(to); n != nil {
|
|
||||||
n.AddNode(from)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// ArcList returns a list of all arcs
|
|
||||||
func (g *Graph) ArcList() []string {
|
func (g *Graph) ArcList() []string {
|
||||||
var ret []string
|
var arcList []string
|
||||||
for i := range g.leaves {
|
for i := range g.leaves {
|
||||||
ret = append(ret, g.leaves[i].ArcList()...)
|
arcList = append(arcList, g.leaves[i].ArcList()...)
|
||||||
}
|
}
|
||||||
return ret
|
return arcList
|
||||||
}
|
}
|
||||||
|
|
||||||
// ChangeRoot changes the graph from starting at oldRoot going to newRoot
|
func (g *Graph) GetPath(fr, to string) []string {
|
||||||
func (g *Graph) ChangeRoot(oldRoot, newRoot string) *Graph {
|
if frN := g.getNode(fr); frN != nil {
|
||||||
// First of all, find the newRoot node
|
return frN.GetPath(to)
|
||||||
ret := New()
|
|
||||||
// The new graph will start with newRoot and have newRoot's leaves
|
|
||||||
var rt *Node
|
|
||||||
if rt = g.GetNode(newRoot); rt == nil {
|
|
||||||
return ret
|
|
||||||
}
|
}
|
||||||
// It'll have one more leaf, it's parent node
|
return []string{}
|
||||||
//rt.addRealNode(g.GetNode(oldRoot))
|
|
||||||
ret.addRealNode(rt)
|
|
||||||
return ret
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (g *Graph) getPath(from, to string) []string {
|
func (g *Graph) getNode(lbl string) *Node {
|
||||||
var ret []string
|
for i := range g.leaves {
|
||||||
// Get the 'from' node
|
if r := g.leaves[i].getNode(lbl); r != nil {
|
||||||
frNode := g.GetNode(from)
|
|
||||||
if frNode == nil {
|
|
||||||
// Couldn't find the starting node
|
|
||||||
return ret
|
|
||||||
}
|
|
||||||
// Just in case we got the same value for both
|
|
||||||
if from == to {
|
|
||||||
return []string{from}
|
|
||||||
}
|
|
||||||
// Found it
|
|
||||||
return frNode.getPath(to)
|
|
||||||
}
|
|
||||||
|
|
||||||
type Node struct {
|
|
||||||
label string
|
|
||||||
leaves []Node
|
|
||||||
}
|
|
||||||
|
|
||||||
func (n *Node) AddNode(lbl string) {
|
|
||||||
n.leaves = append(n.leaves, Node{label: lbl})
|
|
||||||
}
|
|
||||||
|
|
||||||
func (n *Node) addRealNode(nd *Node) {
|
|
||||||
n.leaves = append(n.leaves, *nd)
|
|
||||||
}
|
|
||||||
|
|
||||||
func (n *Node) GetNode(lbl string) *Node {
|
|
||||||
if n.label == lbl {
|
|
||||||
return n
|
|
||||||
}
|
|
||||||
for i := range n.leaves {
|
|
||||||
if r := n.leaves[i].GetNode(lbl); r != nil {
|
|
||||||
return r
|
return r
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Return a graph from 'newRoot's POV
|
||||||
|
func (g *Graph) ChangeRoot(oldRoot, newRoot string) *Graph {
|
||||||
|
root := g.getNode(newRoot)
|
||||||
|
if root == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
ret := New()
|
||||||
|
//pth := g.GetPath(oldRoot, newRoot)
|
||||||
|
if root.parent != nil {
|
||||||
|
root.parent.removeLeaf(root.label)
|
||||||
|
root.parent.parent = root
|
||||||
|
root.addWholeNode(root.parent)
|
||||||
|
root.parent = nil
|
||||||
|
}
|
||||||
|
ret.addWholeNode(root)
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func (g *Graph) addWholeNode(n *Node) {
|
||||||
|
g.leaves = append(g.leaves, *n)
|
||||||
|
}
|
||||||
|
|
||||||
|
type Node struct {
|
||||||
|
label string
|
||||||
|
leaves []Node
|
||||||
|
parent *Node
|
||||||
|
}
|
||||||
|
|
||||||
|
func (n *Node) AddNode(lbl string) {
|
||||||
|
nn := Node{label: lbl, parent: n}
|
||||||
|
n.leaves = append(n.leaves, nn)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (n *Node) addWholeNode(nd *Node) {
|
||||||
|
n.leaves = append(n.leaves, *nd)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (n *Node) removeLeaf(lbl string) {
|
||||||
|
for i := range n.leaves {
|
||||||
|
if n.leaves[i].label == lbl {
|
||||||
|
n.leaves = append(n.leaves[:i], n.leaves[i+1:]...)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func (n *Node) ArcList() []string {
|
func (n *Node) ArcList() []string {
|
||||||
var ret []string
|
var ret []string
|
||||||
for i := range n.leaves {
|
for i := range n.leaves {
|
||||||
ret = append(ret, n.leaves[i].label+" -> "+n.label)
|
// Append this arc
|
||||||
|
ret = append(ret, n.label+" -> "+n.leaves[i].label)
|
||||||
|
// Append all sub-arcs
|
||||||
ret = append(ret, n.leaves[i].ArcList()...)
|
ret = append(ret, n.leaves[i].ArcList()...)
|
||||||
}
|
}
|
||||||
return ret
|
return ret
|
||||||
}
|
}
|
||||||
|
|
||||||
func (n *Node) getPath(to string) []string {
|
// GetPath returns a string slice of all leaves leading to 'to'
|
||||||
|
func (n *Node) GetPath(to string) []string {
|
||||||
ret := []string{n.label}
|
ret := []string{n.label}
|
||||||
if n.label == to {
|
if n.label == to {
|
||||||
return ret
|
return ret
|
||||||
}
|
}
|
||||||
var i int
|
for i := range n.leaves {
|
||||||
var found bool
|
if toN := n.leaves[i].getNode(to); toN != nil {
|
||||||
for i = range n.leaves {
|
// This is the leaf to follow
|
||||||
if n.leaves[i].GetNode(to) != nil {
|
return append(ret, n.leaves[i].GetPath(to)...)
|
||||||
found = true
|
|
||||||
break
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if !found {
|
// Couldn't get there
|
||||||
// We didn't find a path... :(
|
return []string{}
|
||||||
return ret
|
}
|
||||||
}
|
|
||||||
// n.leaves[i] should be the right leaf now
|
// Returns the node with label lbl or nil
|
||||||
return append(ret, n.leaves[i].getPath(to)...)
|
func (n *Node) getNode(lbl string) *Node {
|
||||||
|
if n.label == lbl {
|
||||||
|
return n
|
||||||
|
}
|
||||||
|
for i := range n.leaves {
|
||||||
|
if r := n.leaves[i].getNode(lbl); r != nil {
|
||||||
|
return r
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
@ -12,8 +12,12 @@ func PrintGraph(g *Graph) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func PrintNode(n *Node, lvl int) {
|
func PrintNode(n *Node, lvl int) {
|
||||||
strings.Repeat(" ", lvl)
|
fmt.Print(strings.Repeat(" ", lvl))
|
||||||
fmt.Println(n.label)
|
if n.parent == nil {
|
||||||
|
fmt.Println("{label:", n.label, "}")
|
||||||
|
} else {
|
||||||
|
fmt.Println("{label:", n.label, ", parent:", n.parent.label, "}")
|
||||||
|
}
|
||||||
for i := range n.leaves {
|
for i := range n.leaves {
|
||||||
PrintNode(&n.leaves[i], lvl+1)
|
PrintNode(&n.leaves[i], lvl+1)
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user