Java-如何使用枚举收集类?

Java-如何使用枚举收集类?,java,Java,让我们假设我有很多矩阵的实现(它们不会从一个扩展到另一个),我希望用户能够看到所有不同的类,以某种枚举或其他方式收集它们,我该怎么做? 它不必是菜单或其他什么,这样我就可以看到所有的类,就像enum一样 例如: MainMatrix matrix= new (ALL THE POSSIBILITIES)(); public enum Matrices{ DIAGONAL_MATRIX(new DiagonalMatrix()); .. .. } Reflections reflections

让我们假设我有很多矩阵的实现(它们不会从一个扩展到另一个),我希望用户能够看到所有不同的类,以某种枚举或其他方式收集它们,我该怎么做? 它不必是菜单或其他什么,这样我就可以看到所有的类,就像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);
而主矩阵是所有矩阵的公共接口

我可以使用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);
我可以这样做吗

  • 在Eclipse中编写上述代码
  • 将光标放在文本
    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呢?所以我们可以设置对角矩阵的值…看看我刚刚发布的答案。你可以给一个枚举一个抽象的方法。一个比我更好更完整的答案,如果我自己这么说的话:-)好的一个阿德里安!