Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/339.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_Inheritance - Fatal编程技术网

对于这个问题,Java中哪种设计模式是最好的?

对于这个问题,Java中哪种设计模式是最好的?,java,inheritance,Java,Inheritance,我有一个CommonTableModel类,它有几个实例方法,每个方法对两个实例变量进行操作 专栏名称 资料 现在,我有六个表,每个表都有不同的列名,但应该有CommonTableModel类的所有实例方法。因此,要将CommonTableModel的实例传递给JTable实例,我应该首先初始化两个实例变量(列名和数据) 问题1。我是否应该创建六个TableModel,每个TableModel对应于每个表,然后将它们扩展到CommonTableModel public class First

我有一个CommonTableModel类,它有几个实例方法,每个方法对两个实例变量进行操作

  • 专栏名称
  • 资料
现在,我有六个表,每个表都有不同的列名,但应该有CommonTableModel类的所有实例方法。因此,要将CommonTableModel的实例传递给JTable实例,我应该首先初始化两个实例变量(列名和数据)

问题1。我是否应该创建六个TableModel,每个TableModel对应于每个表,然后将它们扩展到CommonTableModel

public class FirstTableModel extends CommonTableModel {

    public FirstTableModel() {
        columnNames = {"id", "name"};
        data = {{1, "John"}};
    }
}
在上面的示例中,我尝试初始化继承的数据成员,以便六个TableModel中的每一个都可以根据它们所表示的表填充列名

但是我得到了一个错误,它限制我以这种方式初始化继承的成员。我认为我们不能用这种方式初始化实例变量

然后,如何填充CommonTableModel的instace变量,以便CommonTableModel的实例方法处理我稍后填充的数据

解决方案之一是将数据传递到CommonTableModel的构造函数中,但这样,每次生成表时,我都必须传递整个列名

我很困惑,因为我没有太多编程经验,也不知道好的编码实践

请同时参考一些好的设计模式书籍,以便我能更好地理解设计模式

但是我得到了一个错误,它限制我以这种方式初始化继承的成员。我认为我们不能用这种方式初始化实例变量

未使用
new
初始化的数组是数组常量。只能在声明后直接初始化它们。例如

String[] strings = {"foo", "bar"};
因此,您应该将特定行替换为(假设这些行已经是
CommonTableModel的
受保护的
字段):

根据注释编辑:您当然也可以为此定义构造函数,并使用
super()
调用。这样做的好处是提高了封装程度,即不需要声明字段
受保护
,但现在可以将其声明为
私有
。以下是一个启动示例:

public abstract class CommonTableModel {
    private String[] columnNames;
    private Object[][] data;

    protected CommonTableModel(String[] columnNames, Object[][] data) {
        this.columnNames = columnNames;
        this.data = data;
    }
}


请注意,您仍然需要
new
关键字来实例化它们(rsp在这里的回答是错误的)。您应该只使属性
为静态的
!!它将影响同一类的每个实例。你真的不想那样。也可以在下面看到我的评论。

如果表模型之间的唯一区别是列名,我将把它们作为字符串数组传递给CommonTableModel的构造函数。对所有表使用相同的类,但数据不同。

您的表模型扩展了公共表模型,公共表模型可以在其构造函数中初始化列和数据,我认为您正在寻找这样的模式:

public class CommonTableModel {

    protected CommonTableModel (String[] n, Object[] d) {
        columnNames = n;
        data = d;
    }
}

public class FirstTableModel extends CommonTableModel {

    public FirstTableModel() {

        super(new String[] {"id", "name"}, new Object[][] {{1, "John"}});
    }
}

+1对于“…未使用新的…”初始化的阵列,感谢SRSP,您的答案看起来很棒。请问哪一个更好?这是你的选择。你应该确定的是,不要像你在rsp回答的评论中提到的那样,将它们设置为静态的。它将影响同一类的所有实例!!在通过超类的构造函数之前,还应该使用
new
关键字来实例化它们。我将很快用一个例子编辑答案:如果我在super()调用中传递引用变量,它会显示一个编译时错误,如“在调用超级类型构造函数之前无法引用n”哦。。我记得。。。无法在super()中传递实例变量。我将它们设置为静态,现在它工作正常。如果您将它们设置为静态,它们将具有应用范围。您需要使它们成为CommonTableModel的私有属性,并使用
new[]
实例化数组。同意——看起来他的对象之间的唯一区别在于数据。不同的表模型应该是同一类的单独实例,而不是单独的类。
public class FirstTableModel extends CommonTableModel {
    public FirstTableModel() {
        super(new String[] {"id", "name"}, new Object[][] {{1, "John"}});
    }
}
public class CommonTableModel {

    protected CommonTableModel (String[] n, Object[] d) {
        columnNames = n;
        data = d;
    }
}

public class FirstTableModel extends CommonTableModel {

    public FirstTableModel() {

        super(new String[] {"id", "name"}, new Object[][] {{1, "John"}});
    }
}