【问题标题】:What is the Java Equivalent of Python's property()?Python 的 property() 的 Java 等价物是什么?
【发布时间】:2011-01-04 15:10:43
【问题描述】:

我是 Java 新手,我想创建一些在访问时动态计算的类变量,就像在 Python 中使用 property() 方法一样。但是,我不确定如何描述这一点,所以谷歌搜索向我展示了很多关于 Java“Property”类的信息,但这似乎不是一回事。 Python 的 property() 的 Java 等价物是什么?

【问题讨论】:

  • 感谢您的回复。澄清一下,我知道 Java 通常鼓励您通过 getter 和 setter 访问成员。我的问题是,如果 Java 允许您访问成员(例如 obj.member),并在幕后调用 getter/setter,那么执行 x = obj.member 实际上会执行 x = obj.getMember()。

标签: java python properties


【解决方案1】:

您想在类中创建新的字段/getter/setter 吗?如果您想在运行时执行此操作,则必须使用您的字段和方法创建全新的类,并将其加载到 JVM 中。要创建新类,您可以使用 ASM 或 CGLib 等库,但如果您是 Java 新手,这不是您想要开始的东西。

【讨论】:

    【解决方案2】:

    Java 语言中没有内置这样的工具。您必须自己显式地编写所有的 getter 和 setter。不过,像 Eclipse 这样的 IDE 可以为您生成这个样板代码。

    例如:

    class Point{
      private int x, y;
    
      public Point(int x, int y){
        this.x = x;
        this.y = y;
      }
    
      public void setX(int x){
        this.x = x;
      }
    
      public int getX(){
        return x;
      }
    
      public void setY(int y){
        this.y = y;
      }
    
      public int getY(){
        return y;
      }
    }
    

    您可能想看看Project Lombok,它提供了与Python 的property 有点相似的注释@Getter@Setter

    使用 Lombok,上面的示例简化为:

    class Point{
      @Getter @Setter private int x, y;
    
      public Point(int x, int y){
        this.x = x;
        this.y = y;
      }
    }
    

    【讨论】:

    • 这更接近,但仍然不允许在属性(用作属性)更改时调用动态方法。这是一些调整许多其他对象属性的python代码,只需“设置”uri:bitbucket.org/russellballestrini/miniuri/src/tip/miniuri.py
    • 您可以通过使用@AllArgsConstructor 进一步摆脱定义上面显示的构造函数。
    【解决方案3】:

    它们并不存在。在 Java 中,通常的做法是将成员声明为 privateprotected,并且只允许通过方法访问它们。这通常会导致很多小的getFoo()setFoo(newFoo) 方法。 Python 并没有真正的privateprotected,更常见的是允许直接访问成员。

    【讨论】:

      【解决方案4】:

      正如其他人所指出的,java 有 getter 和 setter,但没有严格的类比。有一个名为Project Lombok 的第三方库,它使用注释在编译时在.class 文件中生成getter 和setter。这可以用来让事情变得不那么冗长。

      【讨论】:

      • -1,当您没有新内容要添加时,您应该投票赞成已经存在的答案。
      • 我的补充是指出 Project Lombok。 GreyMatter 9.0 随后编辑了他的答案以包含它。
      • 不要做出愚蠢的指责。我回答的编辑时间(13:18)早于你回答的发布时间(13:33)。
      【解决方案5】:

      实际上你可以在 Java 中模拟这种行为。

      警告:下面是丑陋的解决方案

      您可以在实用程序类中编写方法,如下面的代码:

      public Object getProperty(String property, Object obj) {
        if (obj != null && property != null) {
             Field field = obj.getClass().getDeclaredField(property);
             field.setAccessible(true);
             try {
                return field.get(obj);
             } catch (Exception ex) {
                return null;
             }
        }
        return null;
      }
      

      您实际上可以将其声明为静态方法,然后将该方法导入需要此行为的类中。

      顺便说一下,Groovy 支持这个功能。

      【讨论】:

      • 请仔细阅读我的帖子。我不是在寻找访问实例成员的函数。我正在寻找一个在引用实例成员时调用函数的功能。例如myobj.attribute = 123;实际上会这样做:myobj.setAttribute(123);
      【解决方案6】:

      内置的 property() 函数与答案中描述的完全相反。这与为成员变量生成 getter 和 setter 无关。它只允许您通过访问属性来调用方法(因此,尽管您只是访问 Python 类中的变量,但将调用一个函数)。 (this post ecplas 如何以及为什么使用它。)
      这就是说,Java 不提供这样的东西。更重要的是,Java 不鼓励属性访问。我想你可以用 Groovy 脚本语言和元魔法来做到这一点。但我不知道该怎么做。

      【讨论】:

        猜你喜欢
        • 2011-04-12
        • 2016-10-30
        • 2011-01-04
        • 2011-04-13
        • 2016-12-06
        • 1970-01-01
        • 1970-01-01
        • 2011-09-03
        • 2011-03-07
        相关资源
        最近更新 更多