3

この文字列を視覚化するという問題に直面しています:

"=IF(A2=1;0;IF(D2=D3;IF(C2=1;TRUE;FALSE);4))";

ご覧のとおり、一般的な構文は Excel の数式に似ているため、IF(TEST; TRUE; FALSE)

私の問題は、ライブラリJUNG2を使用して、この文字列をバイナリ検索ツリー形式で視覚化したいことです。以下に、ツリーがどのように見えるかの例を示します。

ここに画像の説明を入力

現時点で頂点を視覚化するコードを次に示します。

public class SimpleGraphView {
    Graph<Integer, String> g;
    Graph<String, String> n;

    /** Creates a new instance of SimpleGraphView */

    String text = "=IF(A2=1;0;IF(D2=D3;IF(C2=1;TRUE;FALSE);4))";


    public SimpleGraphView() {

        n = new SparseMultigraph<String, String>();

        String str = text;
        String delim = ";";
        StringTokenizer tok = new StringTokenizer(str, delim, true);

        text = text.replace("(", " ");
        String s = text.replace(")", " ");
        String[] r = s.split(";");

        for (int i = 0; i < r.length; i++) {

            //Vertex
            if(r.equals("=IF(")) {
                n.addVertex(r[i].toString());
            }

            if(i % 2==0){
                n.addVertex(r[i].toString());
            } else {
                n.addVertex(r[i].toString());
            }

        }

    }

    /**
     * @param args the command line arguments
     */
    public static void main(String[] args) {
        SimpleGraphView sgv = new SimpleGraphView(); // Creates the graph...
        // Layout<V, E>, VisualizationViewer<V,E>
        Layout<Integer, String> layout = new CircleLayout(sgv.n);
        layout.setSize(new Dimension(300,300));

        VisualizationViewer<Integer,String> vv = new VisualizationViewer<Integer,String>(layout);
        vv.setPreferredSize(new Dimension(350,350));
        // Show vertex and edge labels
        vv.getRenderContext().setVertexLabelTransformer(new ToStringLabeller());
        vv.getRenderContext().setEdgeLabelTransformer(new ToStringLabeller());

        // Create our "custom" mouse here. We start with a PluggableGraphMouse
        // Then add the plugins you desire.
        PluggableGraphMouse gm = new PluggableGraphMouse(); 
        gm.add(new TranslatingGraphMousePlugin(MouseEvent.BUTTON1_MASK));
        gm.add(new ScalingGraphMousePlugin(new CrossoverScalingControl(), 0, 1.1f, 0.9f));

        vv.setGraphMouse(gm); 
        JFrame frame = new JFrame("Interactive Graph View 3");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.getContentPane().add(vv);
        frame.pack();
        frame.setVisible(true);       


    }
}

配列内の文字列からすべての頂点をレンダリングできますr。私の問題は、これらすべての頂点を適切なエッジに接続する方法がわからないことです。すべての頂点を右のエッジに接続する方法はありますか?

あなたの答えに本当に感謝します!

4

2 に答える 2

2

これを行う最も簡単な方法は、テキストを別の方法で分割することです。addEdgeグラフのメソッドをandに置き換えたことに注意してくださいaddVertex

String[] operands = text.substring(1, text.length()).split("[;()]+");
int numIfs = operands.length / 3; // actually (operands.length - 1) / 3 but int division makes it the same 
String[] nodes = new String[numIfs]; // stores the nodes (test strings)
int[] operandNos = new int[numIfs]; // stores the number of operands the if currently has
int nodesIndex = -1; // the index of the if node currently parsed
for (String s : operands) {
    if (s.equals("IF")) {
        // new if found -> increase position in the "stack" (nodes)
        operandNos[++nodesIndex] = 0;
    } else {
        addVertex(s);
        switch (operandNos[nodesIndex]++) {
            case 0:
                // first operand = node name
                nodes[nodesIndex] = s;
                break;
            case 1:
                // second operand found -> add edge
                addEdge(s, nodes[nodesIndex]);
                break;
            case 2:
                // last operand found -> add edge and go back
                do {
                    addEdge(s, nodes[nodesIndex]);
                    s = nodes[nodesIndex--];
                } while (nodesIndex >= 0 && operandNos[nodesIndex]++ == 2);
                if (nodesIndex >= 0) {
                    // was not the last operand of the IF
                    addEdge(s, nodes[nodesIndex]);
                }
        }
    }
}

の代わりに、グラフのメソッドを使用しますaddEdge。グラフは有向であり、平行なエッジを許可しないため、addVertex使用することをお勧めします。DirectedSparseGraphグラフに頂点を追加するには を使用graph.addVertex(vertexName)し、エッジを追加するには を使用しますgraph.addEdge(edge, sourceVertexName, destinationVertexName)

addEdgeandの実装は次のaddVertexようになります。

void addVertex(String s) {
    n.addVertex(s);
}

void addEdge(String source, String dest) {
    n.addEdge("", source, dest);
}

またはそれらをインライン化します。

于 2014-06-16T14:55:03.237 に答える
0

String をループしているとき、どのノードが親で、どのノードが子であるかを追跡する必要があります。「IF=」条件を入力すると、それが親ノードです。他のノードは、次の「IF=」条件に遭遇するまでその子です (そのノードは前の親の子でもありますが、後続のすべてのノードの親です)。したがって、子と親を aPairに追加し、それをSimpleMultiGraphwithに追加しEdgeType.DIRECTEDます。ドキュメントは、有向エッジが とどのように相互作用するかについて不明確ですが、 に追加する最初のものは発信であり、2番目は着信であるPairと想定しています。ドキュメントが不明確であるため、推測にすぎません。VertexPair

于 2014-06-16T13:47:48.000 に答える