Java JDK 8 IndexedPropertyDescriptor 自 JDK 7 以来已更改为 List 对象

2024-01-08

我有一个简单的问题。我有一个在 Java JDK7 中运行的程序,但由于一些内省更改而无法在 JDK8 中运行。

这是重现该问题的测试程序:

import java.beans.BeanInfo;
import java.beans.IntrospectionException;
import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.util.ArrayList;
import java.util.List;

public class Main {

    public static void main(String[] args) throws IntrospectionException {
        BeanInfo info = Introspector.getBeanInfo(MyListClass.class);
        PropertyDescriptor[] descriptors = info.getPropertyDescriptors();
        for (int i = 0; i < descriptors.length; i++) {
            System.out.println(descriptors[i].getClass().getName() + ":" + descriptors[i].getName());
        }

        System.out.println("\n");

        BeanInfo info2 = Introspector.getBeanInfo(MyIndexedListClass.class);
        PropertyDescriptor[] descriptors2 = info2.getPropertyDescriptors();
        for (int i = 0; i < descriptors2.length; i++) {
            System.out.println(descriptors2[i].getClass().getName() + ":" + descriptors2[i].getName());
        }

        System.out.println("\n");

        BeanInfo info3 = Introspector.getBeanInfo(MyArrayClass.class);
        PropertyDescriptor[] descriptors3 = info3.getPropertyDescriptors();
        for (int i = 0; i < descriptors3.length; i++) {
            System.out.println(descriptors3[i].getClass().getName() + ":" + descriptors3[i].getName());
        }

        System.out.println("\n");

        BeanInfo info4 = Introspector.getBeanInfo(MyIndexedArrayClass.class);
        PropertyDescriptor[] descriptors4 = info4.getPropertyDescriptors();
        for (int i = 0; i < descriptors4.length; i++) {
            System.out.println(descriptors4[i].getClass().getName() + ":" + descriptors4[i].getName());
        }

    }

    public class MyListClass {
        private List<String> myListClass = new ArrayList<String>();

        public List<String> getMyListClass() {
            return myListClass;
        }

        public void setMyListClass(List<String> myListClass) {
            this.myListClass = myListClass;
        }

    }

    public class MyIndexedListClass {
        private List<String> myIndexedListClass = new ArrayList<String>();

        public String getMyIndexedListClass(int index) {
            return myIndexedListClass.get(index);
        }

        public void setMyIndexedListClass(int index, String element) {
            this.myIndexedListClass.set(index, element);
        }

        public List<String> getMyIndexedListClass() {
            return myIndexedListClass;
        }

        public void setMyIndexedListClass(List<String> myIndexedListClass) {
            this.myIndexedListClass = myIndexedListClass;
        }

    }

    public class MyArrayClass {
        private String[] myArrayClass = new String[20];

        public String[] getMyArrayClass() {
            return myArrayClass;
        }

        public void setMyArrayClass(String[] myArrayClass) {
            this.myArrayClass = myArrayClass;
        }

    }

    public class MyIndexedArrayClass {
        private String[] myIndexedArrayClass = new String[20];

        public String getMyIndexedArrayClass(int index) {
            return myIndexedArrayClass[index];
        }

        public void setMyIndexedArrayClass(int index, String myValue) {
            this.myIndexedArrayClass[index] = myValue;
        }

        public String[] getMyIndexedArrayClass() {
            return myIndexedArrayClass;
        }

        public void setMyIndexedArrayClass(String[] myIndexedArrayClass) {
            this.myIndexedArrayClass = myIndexedArrayClass;
        }

    }
}

以下是 JDK 7 日志:

java.beans.PropertyDescriptor:class
java.beans.PropertyDescriptor:myListClass

java.beans.PropertyDescriptor:class
java.beans.IndexedPropertyDescriptor:myIndexedListClass

java.beans.PropertyDescriptor:class
java.beans.PropertyDescriptor:myArrayClass

java.beans.PropertyDescriptor:class
java.beans.IndexedPropertyDescriptor:myIndexedArrayClass

以下是 JDK8 的日志:

java.beans.PropertyDescriptor:class
java.beans.PropertyDescriptor:myListClass

java.beans.PropertyDescriptor:class
java.beans.PropertyDescriptor:myIndexedListClass -> Here is the change

java.beans.PropertyDescriptor:class
java.beans.PropertyDescriptor:myArrayClass

java.beans.PropertyDescriptor:class
java.beans.IndexedPropertyDescriptor:myIndexedArrayClass

我很快就必须使用 JDK8,但这是一个阻碍性的更改,因为我的应用程序不再工作了。我对所有扩展的类都存在这个问题Collection界面(列表、地图……)

该代码已被图书馆使用commons-beanutils-1.8.0来自阿帕奇共享资源。

我正在寻找一个解决方案,一个解决方法,使我的应用程序像以前一样工作,当使用JDK7时,有什么解决方案吗?我不能使用数组代替列表(因为数组没有改变)

以下是官方文档的链接:

JDK7: http://docs.oracle.com/javase/7/docs/api/java/beans/IndexedPropertyDescriptor.html http://docs.oracle.com/javase/7/docs/api/java/beans/IndexedPropertyDescriptor.html

JDK8: http://docs.oracle.com/javase/8/docs/api/java/beans/IndexedPropertyDescriptor.html http://docs.oracle.com/javase/8/docs/api/java/beans/IndexedPropertyDescriptor.html


编辑:我找到了我的解决方案,我的问题与struts 1.3有关。我必须在 ActionForm 中重命名索引 getter/setter :http://www.coderanch.com/t/55172/Struts/Indexed-Properties http://www.coderanch.com/t/55172/Struts/Indexed-Properties


嗯,规范明确指出IndexedPropertyDescriptor可能有其他基于数组的访问器方法,仅此而已。这一点没有改变。你这里有的是矛盾的定义简单的属性方法List<String>类型化属性和索引String同名财产。这List基于方法从未与索引属性相关联。

所以改变的是哪些冲突的属性使其进入BeanInfo以及哪些将被删除。此行为可能取决于未指定的顺序HashMap或类似的。可能还有其他因素。因此,不要将其视为 Java 7 与 Java 8 的问题,而只是依赖于实现的行为,该行为也可能在替代的 Java 7 实现之间发生变化。

有两种方法可以解决这个问题。您可以通过重命名属性之一来解决冲突:

public class MyIndexedListClass {
    private List<String> myIndexedListClass = new ArrayList<String>();

    public String getMyIndexedListClass(int index) {
        return myIndexedListClass.get(index);
    }

    public void setMyIndexedListClass(int index, String element) {
        this.myIndexedListClass.set(index, element);
    }

    public List<String> getMyIndexedListClassAsList() {
        return myIndexedListClass;
    }

    public void setMyIndexedListClassAsList(List<String> myIndexedListClass) {
        this.myIndexedListClass = myIndexedListClass;
    }
}

然后,所有 Java 版本的行为都相同,但它的副作用是现在将两个不同的属性视为不同名称的属性。


另一种方法是保持方法不变,但显式删除List基于属性描述符识别的方法。换句话说,使在一次实现中发生的并且似乎是您想要的行为变得明确。

public class MyIndexedListClass {
    private List<String> myIndexedListClass = new ArrayList<String>();

    public String getMyIndexedListClass(int index) {
        return myIndexedListClass.get(index);
    }
    public void setMyIndexedListClass(int index, String element) {
        this.myIndexedListClass.set(index, element);
    }
    public List<String> getMyIndexedListClass() {
        return myIndexedListClass;
    }
    public void setMyIndexedListClass(List<String> myIndexedListClass) {
        this.myIndexedListClass = myIndexedListClass;
    }
}
static // in your example all classes are inner classes
public class MyIndexedListClassBeanInfo extends SimpleBeanInfo {
  private PropertyDescriptor[] properties;

  public MyIndexedListClassBeanInfo() throws IntrospectionException {
    PropertyDescriptor[] p=Introspector.getBeanInfo(MyIndexedListClass.class,
        Introspector.IGNORE_IMMEDIATE_BEANINFO).getPropertyDescriptors();
    ArrayList<PropertyDescriptor> list=new ArrayList<>(p.length+1);
    for(PropertyDescriptor d: p)
      if(!d.getName().equals("myIndexedListClass")) list.add(d);
    list.add(new IndexedPropertyDescriptor("myIndexedListClass",
        MyIndexedListClass.class, null, null,
        "getMyIndexedListClass", "setMyIndexedListClass"));
    properties=list.toArray(new PropertyDescriptor[list.size()]);
  }

  @Override
  public PropertyDescriptor[] getPropertyDescriptors() {
      return properties;
  }
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Java JDK 8 IndexedPropertyDescriptor 自 JDK 7 以来已更改为 List 对象 的相关文章

随机推荐

  • 动态组装模型的 Code First 迁移

    我的数据库模型 有时称为 context 在启动时根据安装的服务和 或插件动态组装 插件和服务通过我的 IoC 容器导出它们的模型定义片段 应用程序核心会在启动时拾取它们并运行它们 DbContext OnModelCreating方法被调
  • 如何为 Mac OS 创建 .app 单包

    我正在尝试为我的 mono 程序创建一个 app 捆绑包以在 Mac OS X 上运行 但尽管阅读了几乎所有有关 macpack 和捆绑 mono 的文章和文档 但这些方法都不起作用 使用 macpack 将二进制文件成功捆绑到 app 包
  • 使用属性文件代替静态最终变量

    我有许多带有静态最终字段的类 它们用作默认值或配置 创建全局配置文件的最佳方法是什么 我应该将这些字段移至单个静态类 使用属性文件还是什么 编辑 我需要在 java 类和 xhtml 页面中使用这个值 价值观不依赖于环境 我可以编译项目来设
  • Electron 和 window 之间的 IPC 通信不起作用

    我正在尝试编写我的第一个基于 Electron Boilerplate 的 Electron 应用程序 我正在尝试从主 Electron 进程发送一条简单的消息到我的窗口中 但似乎该消息没有发送 我所执行的主要代码如下 background
  • 在夏时制时将日期移动一小时

    我正在逐行处理文件 每行都有一个日期 格式如下 YYMMDD HHMM 该文件基本上每 15 分钟记录一次读数 录制时使用了所在时区的夏令时 我遇到的问题是在春季和秋季期间 记录是重复发生回退时的日期和发生回退时的间隙 后备示例 14110
  • 使用Jersey客户端进行POST操作

    在 Java 方法中 我想使用 Jersey 客户端对象对 RESTful Web 服务 也使用 Jersey 编写 执行 POST 操作 但不确定如何使用客户端发送将用作 FormParam 的值在服务器上 我可以很好地发送查询参数 我自
  • 模板和自定义功能;恐慌:函数未定义

    Using html template我正在尝试在模板中使用我自己的函数之一 不幸的是我无法使用 go 模板的函数映射功能 我得到的只是以下错误 go run test go panic template tmpl html 5 funct
  • 二叉搜索树的递归中序遍历

    我想在二叉搜索树 BST 中实现递归中序 我使用两个结构构建了一棵树 Node and Tree 我的代码到目前为止还没有工作 主要是因为类型不匹配Node inorder pub struct Node
  • 导出所有 Azure AD 组及其成员 (PowerShell)

    我见过很多关于导出群组和获取成员的帖子 但奇怪的是不是两者都涉及 基本上 我需要每个 AD 组及其相应成员的 csv 文件或类似文件 我认为这需要从 Azure 完成 因为我们有多个域和 Office 365 incloud 组 Azure
  • 使用 Python 从 PDF 中提取文本及其字体详细信息(样式、大小、颜色、斜体等)[关闭]

    Closed 这个问题不符合堆栈溢出指南 help closed questions 目前不接受答案 我希望使用 Python 从 PDF 中提取文本及其字体详细信息 样式 大小 颜色 斜体等 我需要提取文本及其元数据以用于翻译目的 任何人
  • async/await 和 ES6 生成器的收益之间的区别

    我刚刚读了这篇精彩的文章 发电机 https www promisejs org generators 它清楚地突出显示了这个函数 它是一个用于处理生成器函数的辅助函数 function async makeGenerator return
  • Cordova 2.8.1:ios 上带有 photolibarary 源的camera.getPicture

    使用 cordova 2 8 1 我试图用 photolibrary 做一个camera getPicture 它似乎适用于 Android 但不适用于 iOS 下面是我如何调用 getPicture 代码 在装有 iOS 6 的 iPho
  • 基于 REST 的简单程序中的 HTTP 500 内部服务器错误。从服务器接收/发送响应时对 GET 和 POST 感到困惑

    我第一次使用 REST 服务实现基本的客户端服务器架构 这次 我通过包含更多的类和服务 并在客户端和服务器之间共享类对象作为参数 使事情变得更加复杂 我正在 ApacheTomcat7 上运行服务器 它正在成功执行 当我运行我的客户端时 它
  • 如何在启动时检测iPad的界面旋转?

    我在让我的 iPad 应用程序在我初始化的第一个 UIViewController 中检测其 interfaceOrientation 时遇到问题 在代码中 事实上 如果我跟踪 application statusBarOrientatio
  • 使用“gcloud build”时 Dockerfile COPY 命令缺少单个文件

    我遇到了一个令人难以置信的令人沮丧的问题 Dockerfile 中的 COPY 命令成功复制了除一个之外的所有应用程序文件 我没有 dockerignore 文件 所以我知道该文件不会以这种方式从构建中排除 注意 我确实有一个 gitign
  • 使用channelId获取YouTube频道个人资料图片

    因此 我尝试使用channelId 获取YouTube 频道的频道个人资料图片 我想简单地通过将channelId 添加到URL 并以这种方式获取图像来完成此操作 Facebook 有类似的东西 你可以使用这个 URL http graph
  • 使用 Symfony3.3 将存储库注入服务时出错

    我有一个由服务层和存储库层组成的应用程序 对于服务和存储库 我都声明了接口 并在控制器中注入服务的接口 并且服务被注入存储库的接口 这一切都是通过将 autowire 设置为 true 来完成的 当我在注入的服务之一上调用方法时 只要我不调
  • 使用 get_meta_tags() 函数检索同名元

    我正在尝试检索带有 php 的网页获取元标签 https www php net manual fr function get meta tags php功能 担心的是我的网页包含两个相同的元 And get meta tags 似乎只想检
  • 如何正确、安全地释放 C 中使用嵌套结构的所有内存?

    我嵌套了四层不同的结构 代码如下 typedef struct System system typedef struct College college typedef struct Student student typedef stru
  • Java JDK 8 IndexedPropertyDescriptor 自 JDK 7 以来已更改为 List 对象

    我有一个简单的问题 我有一个在 Java JDK7 中运行的程序 但由于一些内省更改而无法在 JDK8 中运行 这是重现该问题的测试程序 import java beans BeanInfo import java beans Intros