我大量使用 Java.lang.Class.getField()
方法,该方法需要 String
变量作为参数。我面临的问题是,当我更改 getField()
所指的字段名称时,Eclipse 不会警告我参数无处指向(因为它是 String
)并且我最终发现方法工作不正常而未被注意到。
到目前为止,我可以看到两种出路。它要么在每个 getField()
调用周围使用 try-catch
block ,然后运行应用程序以查看下一行将引发异常。修复它并留意下一个异常。或者每次我更改字段名称时,它都会使用查找/替换功能来手动查找字符串值并替换它。在这种情况下是否有更友好(即自动)的方法来更新字符串参数?
也许有一个方法(我找不到)接受完整的字段路径作为非字符串参数并返回一个 Field
对象?类似于 turnToFieldObject(car.speed)
返回与 speed
字段对应的 Field
对象,以便 Eclipse 会自动检查是否存在这样的字段 汽车.速度
。
PS
首先感谢您的回复。
我发现你们很多人都认为我过多地使用了反射。这就是为什么我觉得我需要添加额外的解释,并且也很高兴听到建议。
我正在进行一项关于社会进化建模的研究,我需要实体进化出它们一开始就不具备的新功能。在我看来,添加新字段来表示一些进化变化比向数组或集合添加新元素更容易理解。而且任务表明我不应该知道将会发展什么功能。这就是为什么我如此依赖反射(reflection)。
最佳答案
据我所知,没有这样的方法。您传递一个引用(如果它是一个对象)或值(如果它是原始值);有关最初分配给它们的变量的所有数据在运行时不可用。
这是使用反射的巨大缺点,如果您以这种方式“大量”使用此功能,那么您可能做错了什么。为什么不使用 getter 和 setter 直接访问该字段?
不要误会我的意思,反射有其用途(例如,当您想要扫描具有某些注释的字段并注入(inject)它们的值时),但是如果您使用简单的字符串按名称引用字段或方法,您也可以直接访问字段或方法。这意味着您事先了解该领域。如果它是私有(private)的,那么可能有一个将其封装的原因。由于过度使用反射,您将失去内容辅助和重构的可能性。
如果您对社会进化进行建模,我会采用更灵活的解决方案。在运行时添加新字段是(几乎?)不可能的,因此您基本上被迫为每个实体实现一个新类,并在每次实体“进化”时创建一个新对象。这就是为什么我建议您采用以下解决方案之一:
使用
Map<String, Object>
存储实体的属性。这是一个非常灵活的解决方案,它允许您轻松添加和删除“字段”,但会丢失其类型数据。检查实体是否拥有某种属性(property)将是一个便宜的contains
打电话。如果您确实想坚持使用一百万个自定义类,除了字段之外,还可以使用带有 getter 和 setter 的接口(interface)。例如,转换
private String name
至interface Named { String getName(); void setName(String name); }
。这更容易重构并且不依赖反射。一个类可以根据需要实现任意多个接口(interface),因此这非常类似于现场解决方案,只不过它允许您在迫切需要时使用额外的逻辑创建自定义 getter/setter。确定实体是否具有某种属性是entity instanceof MyInterface
调用,这仍然比反射便宜。
关于java - 检查字段名对应的String参数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35605756/