Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/oop/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java创建方法中的抽象类_Java_Oop_Object_Abstract Class_Abstract - Fatal编程技术网

Java创建方法中的抽象类

Java创建方法中的抽象类,java,oop,object,abstract-class,abstract,Java,Oop,Object,Abstract Class,Abstract,我有一个关于Java中抽象类的问题。 我创建了如下抽象类: public class userClass { private String email; String accountType; account account; public userClass(String email, String accountType){ this.setEmail(email); this.setAccountType(accountType); if(accountTyp

我有一个关于Java中抽象类的问题。 我创建了如下抽象类:

public class userClass {
private String email;
String accountType;
account account;

public userClass(String email, String accountType){
    this.setEmail(email);
    this.setAccountType(accountType);

     if(accountType.equals("basic")){
          this.account = new basicAccount();
     } 
     else if(accountType.equals("premium")){
          this.account = new premiumAccount();
     }
}

正如您所看到的,我有两种类型的帐户:基本帐户和高级帐户,它们都是帐户抽象类的扩展。现在我只想向premium类添加方法,但当我尝试这样做时,我收到一个错误,说我必须在account类中实现它,这是我不想要的。有没有可能用另一种方式呢?为了避免在account和basicAccount类中放置空方法,如果您有一个
account
类,您可以:

public abstract class Account{
    public abstract void doSomethingAccountLike();
    //more stuff
}
您可以有子类:

public class BasicAccount extends Account{
    public void doSomethingAccountLike(){
        //implementation specific to basic accounts
    }
}

public class PremiumAccount extends Account{
    public void doSomethingAccountLike(){
        //implementation specific to premium accounts
    }

    public void doSomethingPremiumLike(){
        //something that only makes sense
        // in the context of a premium account
    }
}
方法
doSomethingPremiumLike()
仅在您有
PremiumAccount
实例时可用,即:

public class AccountDemo{
    public static void main(String[] args){
        PremiumAccount premium = new PremiumAccount();
        BasicAccount basic = new BasicAccount();
        Account generalAccount = premium;

        //valid- the compiler knows that the
        //premium object is an instance of the
        //premium class
        premium.doSomethingPremiumLike();

        //Would cause a compile error if uncommented.
        //The compiler knows that basic is an instance
        //of a BasicAccount, for which the method
        //doSomethingPremiumLike() is undefined.
        //basic.doSomethingPremiumLike();

        //Would generate a compiler error if uncommented.
        //Even though generalAccount actually refers to
        //an object which is specifically a PremiumAccount,
        //the compiler only knows that it has a reference to
        //an Account object, it doesn't know that it's actually
        //specifically a PremiumAccount. Since the method
        // doSomethingPremiumLike() is not defined for a general
        //Account, this won't compile
        //generalAccount.doSomethingPremiumLike();

        //All compile- all are instances of Account
        //objects, and the method doSomethingAccountLike()
        //is defined for all accounts.
        basic.doSomethingAccountLike();
        premium.doSomethingAccountLike();
        generalAccount.doSomethingAccountLike();
    }
}
您的问题

在我看来,您的问题可能是在类
UserClass
中,您有一个字段
帐户
。在构造函数中,可以将
new BasicAccount()
new PremiumAccount()
分配给字段
帐户。这很好,但一旦您这样做,编译器就不再知道在任何给定情况下,
account
字段是指
PremiumAccount
实例还是
BasicInstance
。这意味着,如果您尝试调用
account.doSomethingPremiumLike()
,将出现编译器错误。您可以在运行时绕过此限制:

UserClass
的某个地方:

if(account instanceof PremiumAccount){
    //if we're sure that account is actually a PremiumAccount,
    //cast it to a PremiumAccount here to let the compiler know
    //that doSomethingPremiumLike() can be called 
   ((PremiumAccount)account).doSomethingPremiumLike();
}


注意:我已将类的名称更改为以大写字母开头,这是Java和大多数其他OOP语言中的常见约定。养成遵守此惯例的习惯有助于他人阅读您的代码。

因此,如果您有
帐户
类,您可以:

public abstract class Account{
    public abstract void doSomethingAccountLike();
    //more stuff
}
您可以有子类:

public class BasicAccount extends Account{
    public void doSomethingAccountLike(){
        //implementation specific to basic accounts
    }
}

public class PremiumAccount extends Account{
    public void doSomethingAccountLike(){
        //implementation specific to premium accounts
    }

    public void doSomethingPremiumLike(){
        //something that only makes sense
        // in the context of a premium account
    }
}
方法
doSomethingPremiumLike()
仅在您有
PremiumAccount
实例时可用,即:

public class AccountDemo{
    public static void main(String[] args){
        PremiumAccount premium = new PremiumAccount();
        BasicAccount basic = new BasicAccount();
        Account generalAccount = premium;

        //valid- the compiler knows that the
        //premium object is an instance of the
        //premium class
        premium.doSomethingPremiumLike();

        //Would cause a compile error if uncommented.
        //The compiler knows that basic is an instance
        //of a BasicAccount, for which the method
        //doSomethingPremiumLike() is undefined.
        //basic.doSomethingPremiumLike();

        //Would generate a compiler error if uncommented.
        //Even though generalAccount actually refers to
        //an object which is specifically a PremiumAccount,
        //the compiler only knows that it has a reference to
        //an Account object, it doesn't know that it's actually
        //specifically a PremiumAccount. Since the method
        // doSomethingPremiumLike() is not defined for a general
        //Account, this won't compile
        //generalAccount.doSomethingPremiumLike();

        //All compile- all are instances of Account
        //objects, and the method doSomethingAccountLike()
        //is defined for all accounts.
        basic.doSomethingAccountLike();
        premium.doSomethingAccountLike();
        generalAccount.doSomethingAccountLike();
    }
}
您的问题

在我看来,您的问题可能是在类
UserClass
中,您有一个字段
帐户
。在构造函数中,可以将
new BasicAccount()
new PremiumAccount()
分配给字段
帐户。这很好,但一旦您这样做,编译器就不再知道在任何给定情况下,
account
字段是指
PremiumAccount
实例还是
BasicInstance
。这意味着,如果您尝试调用
account.doSomethingPremiumLike()
,将出现编译器错误。您可以在运行时绕过此限制:

UserClass
的某个地方:

if(account instanceof PremiumAccount){
    //if we're sure that account is actually a PremiumAccount,
    //cast it to a PremiumAccount here to let the compiler know
    //that doSomethingPremiumLike() can be called 
   ((PremiumAccount)account).doSomethingPremiumLike();
}



注意:我已将类的名称更改为以大写字母开头,这是Java和大多数其他OOP语言中的常见约定。养成这样的习惯,帮助别人阅读你的代码是很好的。

这个类不是抽象的。。。您发布了正确的代码吗?没有理由不能将方法添加到抽象类的一个扩展中,但不能添加到基类中。请发布给您错误的实际代码以获取更多帮助。请添加
account
类的定义。account类是一个抽象类。我想为account.shareFile(fileReceiver,fileName)创建方法;但是我不想在基本帐户中使用这种方法,因为我的假设是基本帐户不允许这种共享。@Gariable请发布实际给出错误的代码。没有这些,我们就没有什么可以做的了。这个类不是抽象的。。。您发布了正确的代码吗?没有理由不能将方法添加到抽象类的一个扩展中,但不能添加到基类中。请发布给您错误的实际代码以获取更多帮助。请添加
account
类的定义。account类是一个抽象类。我想为account.shareFile(fileReceiver,fileName)创建方法;但是我不想在基本帐户中使用这种方法,因为我的假设是基本帐户不允许这种共享。@Gariable请发布实际给出错误的代码。没有这一点,我们就无能为力了。是的,没错。这就是它看起来的样子,但在我的代码中,当我创建对象时,我使用account newAccount=newbasicaccount()来实现这一点;正因为如此,我收到一个错误,说我必须将这个新方法doSomethingPremiumLike()也放在account抽象方法中(以及我希望避免的basicAccount中的内容),您应该以另一种方式创建它-basicAccount account=new PremiumAccount()。然后将account变量强制转换为PremiumAccount,如果您想使用某些特定的方法。但可以用这种方式创建对象吗?Eclipse告诉我,要创建premiumAccount()的新对象,它必须像“account account”或“basicAccount account”一样,现在就完美了!多谢各位@加里亚伯:我想我知道你的问题在哪里了。看看我刚才在你眼睛后面加的东西,没错。这就是它看起来的样子,但在我的代码中,当我创建对象时,我使用account newAccount=newbasicaccount()来实现这一点;正因为如此,我收到一个错误,说我必须将这个新方法doSomethingPremiumLike()也放在account抽象方法中(以及我希望避免的basicAccount中的内容),您应该以另一种方式创建它-basicAccount account=new PremiumAccount()。然后将account变量强制转换为PremiumAccount,如果您想使用某些特定的方法。但可以用这种方式创建对象吗?Eclipse告诉我,要创建premiumAccount()的新对象,它必须像“account account”或“basicAccount account”一样,现在就完美了!多谢各位@加里亚伯:我想我知道你的问题在哪里了。看到我刚刚在你的问题后添加的内容了吗