4

这将有点难以解释,但我会尽力而为。

我想要多个项目,当单击时,每个项目都有不同的结果。其余的,它们都具有相同的变量。所以基本上,我有一个 Item 类,还有 Ball、Rope、Book 的子类,还有很多很多的子类。如果我愿意,我希望能够轻松添加项目。Item 类具有字符串名称、字符串描述和每个子类都覆盖的方法“onUse”。

我想尽可能动态地处理这个问题,这意味着我想在我的框架/活动中使用一个方法(这适用于 Android,但适用于 Java)来执行该方法。

我将其用于单一方法:

public void useItem(Item i)
{
    i.onUse();
}

我的问题是我将不同的项目保存在数据库中。我想从数据库中随机抓取其中一项并实例化它;除了我无法知道将它实例化为哪个子类。我尝试将数据类型保存在数据库中,但这并没有真正奏效......伪代码:

//Database cursor stuff
//...
                String itemType = c.getString(6);

                //Get the class name if possible
                Class itemClass= null;
                try {
                    itemClass = Class.forName(itemType);
                } catch (ClassNotFoundException)
                    e.printStackTrace();
                }

            Item l = null;
            // Check here what type it is!
            if (itemClass.equals(Ball.class)) {
                l = new Ball(name,description);

            } else if(lootClass.equals(Book.class)){

                l = new Book(name,description); 
            }

看到有这么多不同的项目,这并不是很好,因为我必须遍历大量的类(加上我经常得到 ClassNotFoundException)

你说什么,StackOverflow?最好的方法是什么?

4

2 回答 2

2

在您的情况下,我将使用工厂方法模式(又名工厂模式)。

工厂方法模式是一种创建模式。创建模式通过隐藏对象的创建方式来抽象对象实例化过程,并使系统独立于对象创建过程。

让我们尝试实现它应该如何工作:

模型

public abstract class Model {  
   protected abstract void init();
}

public class Book extends Model {
 @Override
protected void init() {
    System.out.println("I'm a Book");
}
}

public class Ball extends Model {
    @Override
protected void init() {
    System.out.println("I'm a Ball");
}
}

数据库模型工厂

public abstract class DbModelFactory {
    public abstract Model getModel(int modelId);
}

SimpleDbModelFactory

public class SimpleDbModelFactory extends DbModelFactory  {

    @Override
    public Model getModel(int modelId) {
        Model model = null;
        if(modelId == Const.MODEL_BOOK) {

            model = new Book();
        }
        else if(modelId == Const.MODEL_BALL) {

            model = new Ball();
        }
        else {// throw Exception

        }
        return model;
    }
}

常量

public class Const {
    public static final int MODEL_BOOK = 0;
    public static final int MODEL_BALL = 1;
}

启动器

public class Launcher {
  public static void main(String[] args) {
    DbModelFactory factory  = new SimpleDbModelFactory();
    Model book = factory.getModel(0);
    book.init(); // I'm a Book

    Model ball = factory.getModel(1);
    ball.init(); //I'm a Ball
    }
}

工厂模式返回几个产品子类之一。您应该使用工厂模式如果您有一个超类和许多子类,并且根据提供的一些数据,您必须返回其中一个子类的对象

现在我们有 2Models book并且ball我们不在乎两者实际上都是Model.

于 2013-10-14T21:42:57.233 回答
1

工厂模式可能是要走的路。如果您将完全限定名称存储在数据库中,那么您可以创建一个读取值并使用以下命令实例化新项目的工厂:

Item item = (Item) Class.forName(theDBField).newInstance();
item.setName(name);
item.setDescription(desc);

这意味着一个更简洁的工厂,它不必知道它可以构建的所有类。我真的不喜欢每次添加新实现时都必须更新工厂,这是避免它的简单方法。

为此,您必须将 getter 和 setter 添加到项目界面。

于 2013-10-14T21:59:33.250 回答