2010-06-16 68 views
0

我有两个班,derivedClassAderivedClassB这两者延长parentClass 我声明了var o:parentClass然后根据这是怎么回事,我想投oderivedClassA型或derivedClassB的任何福利。铸造,AS3

从本质上讲,这样的:

var o:parentClass 

... 

if(shouldUseA) 
    o = new derivedClassA(); 
else 
    o = new derivedClassB(); 
o.doSomething(); 

但它不工作,我收到各种错误。这不是类继承是如何工作的吗?我觉得我错过了一些非常重要的东西,但我无法弄清楚什么。我应该使用接口吗?还有另一种做我想做的事情的方式吗?

编辑澄清:
- doSomething()parentClass定义为public,并在派生类为override public function doSomething()
- 我得到的错误是“通过静态类型父类的引用调用可能未定义的方法DoSomething的“。和“将derviedClassA类型的值隐式强制为无关类型父类”

+0

你会得到什么错误?是在parentClass中定义的doSomething还是仅在子类中定义的? – luke 2010-06-16 20:59:13

+3

你的问题与你的例子不同。在你的问题中,你说你正在声明'var o:classA'并试图将它转换为'classB',这将无法工作。但是,您应该能够执行示例所说的内容,即声明'var o:parentClass',然后为其分配一个其子类的值。 你想要做什么,你会得到什么样的错误? 另外,正如上面所述:doSomething是在父类中定义的吗?如果没有,你需要预先施放(即:classA(o).doSomething();) – 2010-06-16 21:46:09

+3

而且,在标准方面你应该使用CapitalizedNamesForClasses。不应该影响你的结果,但只是为了让你知道这些名字是非常规的。 – 2010-06-16 21:47:57

回答

0

我将使接口能够执行您所要求的操作。这你你不必投射变量,它会让你访问你的doSomething函数。 这是一个使用你的结构的小例子: 请注意,所有的类都在同一个根包中,因此没有导入语句。

MainApp.as(这是默认的应用程序)

package 
{ 
    import flash.display.Sprite; 

    public class MainApp extends Sprite 
    { 
     private var parentClass : IParent; 
     private var doA : Boolean = false; 

     public function MainApp() 
     { 

      if (doA) 
      parentClass = new DerivedClassA(); 
      else 
      parentClass = new DerivedClassB(); 

      parentClass.doSomething(); 
     } 
    } 
} 

Parent.as

package 
{ 
    import flash.display.Sprite; 

    public class Parent extends Sprite 
    { 
     public function Parent() 
     { 
     } 
    } 
} 

DerivedClassA.as

package 
{ 
    public class DerivedClassA extends Parent implements IParent 
    { 
     public function DerivedClassA() 
     { 
      super(); 
     } 

     public function doSomething() : void 
     { 
      trace (this + " done something"); 
     } 
    } 
} 

DerivedClassB.as

package 
{ 
    public class DerivedClassB extends Parent implements IParent 
    { 
     public function DerivedClassB() 
     { 
      super(); 
     } 

     public function doSomething() : void 
     { 
      trace (this + " done something"); 
     } 
    } 
} 

IParent.as

package 
{ 
    public interface IParent 
    { 
     function doSomething():void; 
    } 
} 

正如你可以看到使用界面,调用该函数DoSomething的无铸造。 关于转换变量没有问题,但是这可以为您提供更加结构化的代码,并且可以确保您在实现该接口的类中具有doSomething方法。 希望它可以帮助... 摹运气

+1

我不会推荐这个解决方案。任何类型为接口的东西都将无法访问父类的其他属性。 – 2011-03-29 00:22:03

0

的具体回答您问的问题是这样的:

o["doSomething"](); 

但是,我不建议你这么做。我认为真正的问题是你的父类应该定义doSomething(),那么派生类应该覆盖函数。

1

我以前做过这样的事情:在基类中的虚函数中抛出错误,明显地指出错误地调用它。当我做抽象基类时,我会这样做。

Main.as(文档类)

package 
{ 
    import flash.display.Sprite; 

    public class Main extends Sprite 
    { 
     private var superClassRef:SuperClass; 
     private var idLikeToBuyAnA:Boolean = true; 

     public function Main() 
     { 
      trace("Main()"); 
      if (idLikeToBuyAnA) 
      { 
       superClassRef = new DerivedClassA(); 
      } 
      else 
      { 
       superClassRef = new DerivedClassB(); 
      } 

      superClassRef.doSomething(); 
     } 
    } 
} 

SuperClass.as

package 
{ 
    public class SuperClass 
    { 
     public function SuperClass() 
     { 
     } 

     public function doSomething():void 
     { 
      throw new Error("Override me, I wish I were virtual!"); 
     } 
    } 
} 

DerivedClassA.as

package 
{ 
    public class DerivedClassA extends SuperClass 
    { 
     public function DerivedClassA() 
     { 
     } 

     override public function doSomething():void 
     { 
      trace("I'm and A!"); 
     } 
    } 
} 

DerivedClassB.as

package 
{ 
    public class DerivedClassB extends SuperClass 
    { 
     public function DerivedClassB() 
     { 
     } 

     override public function doSomething():void 
     { 
      trace("I'm a B!"); 
     } 
    } 
}