2

次の2つのクラスがあります。

public class Parent{
    static internal const _name:String = "Parent";

    public function get name():String{
        return _name;
    }
}

public class Child{
    static internal const _name:String = "Child";
}

クラスChildのインスタンスを作成し、そのname()getterを呼び出すと、Parentから継承するname()メソッドが呼び出されるため、「Parent」が返されます。もちろん、name()メソッドをオーバーライドすることもできます。

public class Child{
    static internal const _name:String = "Child";

    override public function get name():String{
        return _name;
    }
}

「子」を返します。ただし、メソッドのまったく同じコードを親からコピーする必要があるのはばかげているようです。これを行うためのより簡単な方法はありますか?

4

5 に答える 5

1

「name」プロパティを親のコンストラクターの要件にすることで、別のアプローチを取ります。

public class Parent
{
    static internal var _name : String;

    public function Parent(name : String = "Parent") {
        _name = name;
    }

    public function get name() : String {
        return _name;
    }
}

子クラス:

public class Child extends Parent
{   
    public function Child() {
        super("Child");
    }
}
于 2012-10-05T06:39:37.383 に答える
1

get nameの実装は次のようになります。getterは1つであり、新しいクラスのそれぞれに、独自のpublic staticvar_nameを定義する必要があります。

//in the base class
    public function get name():String 
    {
        var _sName:String;
        if ((this as Object).constructor._name)
        {
            _sName = (this as Object).constructor._name; 
        }
        else
        {
            try
            {
                var o:Object = getSuperClass(this);
                while (o)
                {
                    if (o._name)
                    {
                        _sName = o._name;
                        break;
                    }
                    o =  getSuperClass(o);
                }
            }
            catch (e:*)
            {}
        }
        return _sName;
    }
//as found here: http://www.actionscriptdeveloper.co.uk/getting-the-class-of-an-object-in-as3/
public static function getSuperClass(o: Object): Object
{
    var n: String = getQualifiedSuperclassName(o);
    if (n == null)
        return(null);

    return getDefinitionByName(n);
}

静的メンバーには、コンストラクターオブジェクトから取得できるクラス参照を介してのみアクセスできます。「this」は継承チェーンの現在のクラスを指すため、親クラスでこれを呼び出すことができ、子クラスの子を指します。 。

[編集] 「this」インスタンスで見つからない場合はパブリック静的プロパティ_nameの存在をテストするように変更し、ループ内で親クラスが見つかるまでチェックされます-継承のように:)

私はこの機能を使用してクローンメソッドを作成しています:クローンメソッド実装のヘルパーとしてのコンストラクター

よろしくお願いします

于 2012-10-05T06:56:23.673 に答える
1

まず、静的メソッドまたはプロパティをオーバーライドすることはできません。これらは継承されないため、オーバーライドすることはできません。

次に、定数を複合型として宣言した場合、それは実際には定数ではありません。つまり、オブジェクトの場合はキー/値を変更でき、配列の場合はメンバーを追加/削除できます。

しかし、この機能をより一般的にしたいという願望は理解できます。だから、私がすること:

親と子の両方の外部にいくつかのプロパティがあります。たとえば、クラスXまたはパッケージにありますY。パッケージにしましょうY。したがって、パッケージに辞書を作成し、YそれをそのままにY.namesして、名前のゲッターで次のようにします。

import Y.names;
. . .
public function get name() {
    return names[(this as Object).constructor];
}

名前変数は次のようになります。

package Y {

    public var names:Dictionary = generateNames();

    internal function generateNames():Dictionary {
        var result:Dictionary = new Dictionary();
        result[ChildClass] = "child";
        result[ParentClass] = "parent";
        . . .
        return result;
    }
}

このように、スーパークラスでname getterを実装するだけで十分であり、すべての継承クラスはスーパークラスコードをそのまま使用でき、何も変更する必要はありません。ただし、これは、このクラスに関連するいくつかの(おそらく重要な)情報が他の場所に保存されることを意味します(見つけるのが難しい場合があります。これは、AS3でプログラムする一般的な方法ではありません)。

于 2012-10-05T08:05:12.133 に答える
1

アクセスできない定数を宣言する代わりに、対応する関数内にそのような定数を格納してみませんか?

class Parent {
    ...
    public function get name():String { return 'Parent'; }
}
class Child extends Parent {
    ...
    override public function get name():String { return 'Child'; }
}

ちなみに、ParentクラスがDisplayObjectの子孫である場合は、nameプロパティに注意する必要があります。これは、たとえば、コードを操作することで必要になる場合があるためですgetChildByName()

于 2012-10-05T10:52:30.743 に答える
0

うまくいくように見えるものを見つけました。フィードバックは大歓迎です:

public class Parent{
    prototype._name = "Parent";

    public function get name():String{
        return this["_name"];
    }
}

public class Child{
    prototype._name = "Child";
}
于 2012-10-05T07:50:12.097 に答える