有没有去在Java中动态生成变量的名字?(Is there away to generate Var

2019-06-17 17:45发布

比方说,我需要生成变量从用户(我不知道他们有多少人)持有一些输入。 如果不使用ArrayArrayList (和其他类型的列表和地图),可我的代码生成(可以说) String变量X倍,如姓名( String var001String var002String var003等)? 如果有,请提供的示例代码。

Answer 1:

以下是我已经实现,并帮助我轻松地解决我的解决方案没有太多的障碍的方式。

//创建数组列表

List accountList = new ArrayList(); 




for(int k=0;k < counter;k++){
        accountList.add(k, (String)flowCtx.getValueAt("transitId"+m));
}

迭代循环和添加的对象与指数ArrayList中。

//检索在运行时的对象与索引的帮助

String a = accountList.get(i));


Answer 2:

如果你真的想要做这样的事情,你可以用它做通过字节码生成ASM或其他一些库。

下面是代码,将生成一个名为“foo.bar.ClassWithFields”类,它包含的字段“var0”到“var99”。 当然没有办法比反射其他访问这些领域,因为他们没有在编译时存在,Java是一种静态类型语言。

import org.objectweb.asm.*;
import static org.objectweb.asm.Opcodes.*;

import java.lang.reflect.Field;

public class GeneratedFieldsExperiment {

    public static byte[] generateClassWithFields(int fieldCount) throws Exception {
        ClassWriter cw = new ClassWriter(0);
        FieldVisitor fv;
        MethodVisitor mv;
        AnnotationVisitor av0;

        cw.visit(V1_6, ACC_PUBLIC + ACC_SUPER, "foo/bar/ClassWithFields", null, "java/lang/Object", null);

        for (int i = 0; i < fieldCount; i++) {
            fv = cw.visitField(ACC_PUBLIC, "var" + i, "Ljava/lang/String;", null, null);
            fv.visitEnd();
        }
        {
            mv = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
            mv.visitCode();
            mv.visitVarInsn(ALOAD, 0);
            mv.visitMethodInsn(INVOKESPECIAL, "java/lang/Object", "<init>", "()V");
            mv.visitInsn(RETURN);
            mv.visitMaxs(1, 1);
            mv.visitEnd();
        }
        cw.visitEnd();

        return cw.toByteArray();
    }

    public static void main(String[] args) throws Exception {
        MyClassLoader loader = new MyClassLoader();
        Class<?> c = loader.defineClass("foo.bar.ClassWithFields", generateClassWithFields(100));

        System.out.println(c);
        System.out.println("Fields:");
        for (Field field : c.getFields()) {
            System.out.println(field);
        }
    }

    private static class MyClassLoader extends ClassLoader {
        public Class<?> defineClass(String name, byte[] b) {
            return defineClass(name, b, 0, b.length);
        }
    }
}


Answer 3:

如果不使用数组,ArrayList的(和其他类型的列表和地图)

创建具有这些名称的文件。 希望会为你的教授工作。

或者使用前面提到的Java脚本API:

ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("JavaScript");

engine.put("x", "hello"); // you can add any variable here
// print global variable "x"
engine.eval("println(x);");
// the above line prints "hello"

编辑

好像在内部,这将使用地图:)同样的,属性文件,首选项API,或DOM树(他们使用向量)。 所以,如果你的教授是这么挑剔,使用文件。



Answer 4:

我还没有看到这个回答,所以我会去的。 编写一个程序,只是写出Java源代码。 它的大部分可能是一个模板,你只会有一个循环,只要你想的是会写许多“字符串UserString003”类型变量。

是的,这是可怕的。 但是,正如你所说,这是家庭作业的概念挑战问题,所以只要没有一个失误这对“好”的代码,它可能会解决这个问题。



Answer 5:

命名一样,变量看起来很1980年十岁上下。 含义预面向对象的编程。 所以,如果你曾经建立为生软件 - 不要这么做。

但是,因为它似乎是功课...

当我们谈论Java中的一个命名的变量,我们的意思东西是编译。 不像一些脚本语言中有没有简单的方法在Java中做到这一点。

因此,无论你使用像马库斯Lausberg运行时编译的类建议。
或者你欺骗和使用Java脚本API和利用脚本语言。 这样,你可以在运行时创建(在一个字符串)代码。



Answer 6:

我想你可以在运行时生成一个Java类或可能使用像一些脚本引擎BeanShell的生成变量,你甚至可以通过它的字节码构建类。 但我看不到你将如何使用该变量的代码,您还必须创建代码与变量的工作,或使用反射为...

一个天真的解决方案:
创建与var000所有变量一类var999为每个吸气......但是这并不是真正动态!



Answer 7:

它看起来像你的教授是PHP偏置的功能( 可变变量 ),所以他在想,如果在Java中是可能的。

我个人不认为这是可能的,而不是在你提议的方式。 有什么可以做的是类在运行时生成,使用工具如Javassist是做一个更强大的反射机制。 所以,你可以创建在运行时有你想要的变量(字符串1,字符串等)的类。

但是,不要忘记, 可变变量是一个非常糟糕的技术,这会导致糟糕的代码。 这可能会在极少数情况下是有用的,但我真的不推荐它。



Answer 8:

你的意思是你想生成命名变量

var0,VAR1,VAR2并在代码中使用它们。

有什么区别,当你使用VAR [0],VAR [1],VAR [2],.....

您可以在运行时动态,它实现你正在使用您的正常代码的接口生成的Java类。 然后,你使用编译器(例如JANINO)编译这个类,然后在运行时加载的类。 比你已经创建了一个类动态。

但我不知道,这是否有必要为你的用例。

编辑

我现在不为其USECASE你使用这个参数,而是动态的变量,你可以在Java中使用类似这样的例子在这里

// calculate average
        public static double average( double... numbers )
        {
           double total = 0.0; // initialize total

          // calculate total using the enhanced for statement
          for ( double d : numbers )              
             total += d;                          

          return total / numbers.length;
       } // end method average


Answer 9:

这是不可能的,但是这是使用Java集合的一个完美的候选人。

既可以使用动态分配的数组:

String[] arr = new String[RUNTIME_SIZE];

或可以改变它的列表是在运行时的大小:

List list = new ArrayList<String>();


Answer 10:

我不知道如果我理解正确的你,但如果你要使用动态创建名称为你的变量然后是,肯定 - 我这样做是这样的:

// rndRng() creates random numbers in specified range
// this would output dynamically created variable like "name89"
String myDynamicalyCreatedName = "name" + Utils.rndRng(0, 100);
final UberShader $myDynamicalyCreatedName = new UberShader();

正如你可以看到这一点这里的关键是符号“$”,基本上说:“从这篇迹象后给出字符串创建变量名”,这就是基本上它 - 就像我的一个魅力现在几年.. 。希望这是你想要的东西,它有点帮助解决你的问题。



文章来源: Is there away to generate Variables' names dynamically in Java?