Java-如何使用枚举收集类?
让我们假设我有很多矩阵的实现(它们不会从一个扩展到另一个),我希望用户能够看到所有不同的类,以某种枚举或其他方式收集它们,我该怎么做? 它不必是菜单或其他什么,这样我就可以看到所有的类,就像enum一样 例如:Java-如何使用枚举收集类?,java,Java,让我们假设我有很多矩阵的实现(它们不会从一个扩展到另一个),我希望用户能够看到所有不同的类,以某种枚举或其他方式收集它们,我该怎么做? 它不必是菜单或其他什么,这样我就可以看到所有的类,就像enum一样 例如: MainMatrix matrix= new (ALL THE POSSIBILITIES)(); public enum Matrices{ DIAGONAL_MATRIX(new DiagonalMatrix()); .. .. } Reflections reflections
MainMatrix matrix= new (ALL THE POSSIBILITIES)();
public enum Matrices{
DIAGONAL_MATRIX(new DiagonalMatrix());
..
..
}
Reflections reflections = new Reflections(...); //see in other use cases
Set<Class<? extends MainMatrix>> subTypes =
reflections.getSubTypesOf(MainMatrix.class);
而主矩阵是所有矩阵的公共接口
我可以使用enum创建与我将选择的选项匹配的新类的实例吗?
例如:
MainMatrix matrix= new (ALL THE POSSIBILITIES)();
public enum Matrices{
DIAGONAL_MATRIX(new DiagonalMatrix());
..
..
}
Reflections reflections = new Reflections(...); //see in other use cases
Set<Class<? extends MainMatrix>> subTypes =
reflections.getSubTypesOf(MainMatrix.class);
我可以这样做吗
main矩阵中
F4
F4
是打开“类型层次结构”视图的Eclipse快捷方式。这将显示当前选定类型的所有子类型。您可以使用库以编程方式执行此操作
例如:
MainMatrix matrix= new (ALL THE POSSIBILITIES)();
public enum Matrices{
DIAGONAL_MATRIX(new DiagonalMatrix());
..
..
}
Reflections reflections = new Reflections(...); //see in other use cases
Set<Class<? extends MainMatrix>> subTypes =
reflections.getSubTypesOf(MainMatrix.class);
反射=新反射(…)//请参阅其他用例
Set如果所有类都是矩阵的实现,那么让它们实现公共接口或扩展公共抽象类可能是有意义的。通过这个简单的2级层次结构,您还可以构建一个通用超类/接口的数组。这里有一个例子来说明我的意思:
public class AA {
public interface MainMatrix {
}
public class MatrixA implements MainMatrix {
}
public class MatrixB implements MainMatrix {
}
public void go() {
MainMatrix[] mainMatrices = new MainMatrix[2];
mainMatrices[0] = new MatrixA();
mainMatrices[1] = new MatrixB();
}
}
一种方法是在枚举中有一个方法来创建矩阵(主要基于您已经编写的内容):
编辑:
只需调用createMatrix
方法为给定枚举创建矩阵:
Matrices type = ...
MainMatrix matrix = type.createMatrix();
或者直接
MainMatrix matrix = DIAGONAL_MATRIX.createMatrix();
我们可以创建某种矩阵工厂:
public class MatrixImplFactory {
IMatrixImpl createMatrix(double[] diagonal) {
return new DiagonalMatrix(diagonal);
}
IMatrixImpl createMatrix(int rows, int cols) {
return new FullMatrix(rows, cols);
}
}
我只需要确保每个矩阵都有不同类型的构造函数
以这种方式制作矩阵实例:
public class Matrix implements IMatrix {
protected IMatrixImpl impl;
MatrixFacotry factory;
public Matrix(int rows, int cols) {
impl = factory.createMatrix(rows, cols);
}
....
}
我认为这可能是您想要尝试的:
public enum Matricies {
DIAGONAL_MATRIX(new DiagonalMatrix()),
OTHER_MATRIX(new OtherMatrix(4, 4));
private MainMatrix value; // each value of the enum has a value which is an instance of a matrix
Matricies(MainMatrix val) { // enum constructor to set instance of matrix
value = val;
}
public MainMatrix getValue() {
return value;
}
}
要获取对角矩阵的实例,请执行以下操作:
MainMatrix diagMatrix = Matricies.DIAGONAL_MATRIX.getValue();
这里是一个使用带有抽象方法的枚举的解决方案:
public enum MatrixFactory {
/**
* Creates a diagonal matrix
*
* args[0] : a double[] with the diagonal values
*/
DIAGONAL_MATRIX {
@Override
public MainMatrix create(Object[] args) {
double[] diagonal = (double[]) args[0];
return new DiagonalMatrix(diagonal);
}
},
/**
* Creates a full matrix
*
* args[0] : the number of rows
*
* args[1] : the number of columns
*/
FULL_MATRIX() {
@Override
public MainMatrix create(Object[] args) {
int rows = (Integer) args[0];
int cols = (Integer) args[1];
return new FullMatrix(rows, cols);
}
};
public abstract MainMatrix create(Object[] args);
}
用法:
MatrixFactory.DIAGONAL_MATRIX.create(new Object[] {new double[] {1.0, 2.0, 3.0}});
MatrixFactory.FULL_MATRIX.create(new Object[] {4, 4});
另请参见用算术枚举说明这一点的:
public enum Operation {
PLUS { double eval(double x, double y) { return x + y; } },
MINUS { double eval(double x, double y) { return x - y; } },
TIMES { double eval(double x, double y) { return x * y; } },
DIVIDE { double eval(double x, double y) { return x / y; } };
// Do arithmetic op represented by this constant
abstract double eval(double x, double y);
}
不过,我主张建立一个正规的工厂,因为它的用法要清楚得多。在这种情况下,使用枚举并没有增加我能想到的任何好处
public class MatrixFactory {
/**
* Creates a diagonal matrix
*
* @param diagonal the diagonal values
* @return
*/
public static MainMatrix diagonalMatrix(double[] diagonal) {
return new DiagonalMatrix(diagonal);
}
/**
* Creates a full matrix
*
* @param rows the number of rows
* @param cols the number of columns
* @return
*/
public static MainMatrix fullMatrix(int rows, int cols) {
return new FullMatrix(rows, cols);
}
}
用法:
MatrixFactory.diagonalMatrix(new double[] {1.0, 2.0, 3.0});
MatrixFactory.fullMatrix(4, 4);
谢谢你,但是我想为它写一个代码,一个普通的类或者什么的,我不介意技术方面的问题。看看这个问题-也看看这个问题-谢谢你的问题,我不觉得它们对我所问的有用。我提供了一个具体的想法,想知道它是否正确。那么你想找到MainMatrix的所有实现并创建它们的枚举吗?我知道MainMatrix的所有实现,我想知道我是否可以使用enum创建我想要的实例?在问题中,Nir声明所有矩阵类都实现MainMatrix。“通过这个简单的2级层次结构,您还可以构建一个通用超类数组”-这是一个问题,您如何做到这一点?我添加了一个代码片段,说明了我的意思。我想在我发布我的答案后,这个问题被稍微修改了一下,我可能误解了原来的问题。谢谢你的回答,在使用这个枚举之后,我们如何创建对角_矩阵的实例?主矩阵=矩阵。对角矩阵?可以吗?我想我会有一个编译错误,不是吗?@Nir-将它添加到+1以上我的答案中,你刚刚击败了我!(:我建议将所有工厂方法设置为静态,并删除字段“MatrixFactory factory”。然后您可以简单地通过MatrixImplFactory.createMatrix(…)创建一个矩阵。如果您希望允许多个不同的工厂实现(工厂类),则可以将工厂设置为非静态并实现接口这就是所谓的“抽象工厂”模式()。谢谢!:-)但我并没有像我想要的那样选择矩阵的名称。我想知道这个枚举的想法是否可以实现。感谢您的想法,这比创建MatrixImplFactory的实例要好得多。请确保您可以创建此实例的枚举版本。我将在几分钟后发布一个答案来演示。但是,您需要标准化工厂方法的参数(如对象[]args),这不会提高API的可用性。我想,一个普通的工厂才是最好的选择。如果你愿意,你可以用方法名来表示矩阵的名称。天哪,我总是被打败!但是,这个解决方案不允许客户端传递任何创建参数……如果我们要添加一个setter呢?所以我们可以设置对角矩阵的值…看看我刚刚发布的答案。你可以给一个枚举一个抽象的方法。一个比我更好更完整的答案,如果我自己这么说的话:-)好的一个阿德里安!