2012-04-07 10 views
2

これは私の質問hereのフォローアップです。オブジェクトを作成し、Adaのキーワードに基づいてメソッドを呼び出す

プログラムの中で、現在の構造をさらに進めることができないと感じた点がありましたので、私は多くの書き換えを行いました。 Statementタイプはもはや抽象型ではなく、各サブタイプStatementStatementの変数の独自のインスタンスを作成します。また、コンパイラがそれを気に入らなかったので(私のサブタイプは依然として独自のexecuteメソッドを持っています)、ステートメントパッケージから抽象的execute関数を削除しました。受信文の型を変更する必要があるため、execute関数がプロシージャに変更されました。 statementFactory(旧称createStatement)をStatementパッケージに移動しました。ここで

私は取得していますエラーです:

statements-compoundstatements.adb:15:29: expected type "CompoundStatement" defined at statements-compoundstatements.ads:11 
statements-compoundstatements.adb:15:29: found type "Statement'Class" defined at statements.ads:6 

を私はエイダで初心者だけど、私の勘がexecute手順は(書類の「サブクラス」である)CompoundStatementsにあるためということですステートメントの別の「サブクラス」のexecuteメソッドを見ることは決してできません。私が考えることができる唯一の解決策は、executeプロシージャを呼び出すすべてのプロシージャをStatementパッケージにダンプすることですが、これは望ましくないようです。しかし、それでもstmt.allstatementFactoryで作成されたタイプの代わりにStatement'Classタイプとして使用されている理由について説明していません。あなたはコンパイラが好きではなかったので、私はまた、抽象的には書類パッケージから機能を実行削除」と言う

package Statements is 

    type Statement is tagged private; 

    type Statement_Access is access all Statement'Class; 
    ParserException : Exception; 

    procedure createStatement(tokens : Vector; S : out Statement); 
    procedure statementFactory(S: in out Statement; stmt: out Statement_Access); 

--.....A bunch of other procedures and functions..... 

private 
    type Statement is tagged 
     record 
     tokens : Vector; 
     executedtokens : Vector; 
     end record; 

end Statements; 

procedure createStatement(tokens : Vector; S : out Statement) is 
    begin 
     S.tokens := tokens; 
    end createStatement; 

    procedure statementFactory(S: in out Statement; stmt: out Statement_Access) is 
     currenttoken : Unbounded_String; 
     C   : CompoundStatement; 
     A   : AssignmentStatement; 
     P   : PrintStatement; 

    begin 
     currenttoken := getCurrentToken(S); 
     if currenttoken = "begin" then 
     createStatement(S.tokens, C); 
     stmt := new CompoundStatement; 
     stmt.all := Statement'Class(C); 
     elsif isVariable(To_String(currenttoken)) then 
     createStatement(S.tokens, A); 
     stmt := new AssignmentStatement; 
     stmt.all := Statement'Class(A); 
     elsif currenttoken = "print" then 
     createStatement(S.tokens, P); 
     stmt := new PrintStatement; 
     stmt.all := Statement'Class(P); 
    end statementFactory; 

package body Statements.CompoundStatements is 

    procedure execute(skip: in Boolean; C: in out CompoundStatement; reset: out Integer) is 
     stmt: Statement_Access; 
     tokensexecuted: Integer; 
     currenttoken : Unbounded_String; 
    begin 
     match(C, "begin"); 
     currenttoken := getCurrentToken(C); 
     while(currenttoken /= "end") loop 
     statementFactory(C, stmt); 
     execute(skip, stmt.all, tokensexecuted); //ERROR OCCURS HERE 

答えて

5

:ここ

は新しいコードでありますそれ";コンパイラはexecute (skip, stmt.all, tokensexecuted)を呼び出すときにstmt.allがそれにディスパッチするためにexecuteを提供することを知っているので、本当に必要ですか?

だけでなく、拡張型は、その親タイプの属性を継承しない(ので、各CompoundStatementなどがすでにtokensexecutedtokensを持っている)、それは親の基本操作を継承します。親操作がabstractの場合、子は独自の実装を提供する必要があります。そうでなければ、子は独自の(オーバーライド)実装を提供できます。

Ada 95 RationaleWikibooksを参照してください。

+0

さて、 'procedure execute(スキップ:inブール; S:inステートメント; reset:アウト整数)は抽象ですが、' Statement'は抽象的ではないとコンパイラは依然として不平を言っていましたが、以前はその抽象化を行っていたので、コンパイラはそれを気に入らなかった。私は「声明」の要約も記録することを怠ったことが分かった。それは問題を解決するように見えました。問題に時間を費やすと、それは信じられないほど単純なものに変わります。ありがとうございました。 –

+0

私はこのプロジェクトに数週間を費やしていますが、それは月曜日ですが、私はそれが完全に機能しなくても、私はすでに私が以前知らなかったAdaとコーディングについてのトンを学んだように感じます。また、私はそれについての私の理解がずっと良くなっているので、ちょっと少しだけ、あたしが嫌いです。 :) –

+0

うまくいくことを望む! –

関連する問題