如何将java.sql.Array转换为List<MyCustomEnum>?

6

我有一个java.sql.Array类型的rs.getArray("lang"),其中lang字段是character varying[]。 我想将其转换为List<MyEnumLanguage>。例如,我有{fr_FR,en_US},我使用了以下代码进行转换,我的IDE没有显示任何错误:

List<MyEnumLanguage> myEnumLanguageList = (List<MyEnumLanguage>) rs.getArray("lang");

但是它会抛出异常 org.postgresql.jdbc.PgArray cannot be cast to java.util.List

我的MyEnumLanguage如下:

public enum MyEnumLanguage {
    en_US {
        public String getCode() { return "en_US" }
    },
    de_DE {
        public String getCode() { return "de_DE" }
    };

    private MyEnumLanguage() {
    }
}

你不需要解释它,你需要映射它。 - Stultuske
1个回答

4

你不能将数组强制转换为List。你的IDE不显示任何错误,因为转换发生在运行时。

相反,你应该使用Arrays.asList(array)方法,它返回一个包含数组所有元素的列表。 请注意,如果你想要将数组的元素映射到另一个类型,你可以很容易地使用流来完成。例如:

List<MyEnumLanguage> myEnumLanguageList = Arrays.asList(rs.getArray("lang"))
                .stream()
                .map(arrayElement -> convertToMyEnumLanguage(arrayElement))
                .collect(Collectors.toList());

convertToMyEnumLanguage()函数接受你的数组中的一个元素并返回相应的MyEnumLanguage枚举。

请查看这篇文章:https://stackify.com/streams-guide-java-8/

更新

一开始我理解错误了问题。在使用Arrays.asList()之前,您必须先将PgArray转换为普通的java数组。

可以使用PgArray.getArray()方法来完成此操作,然后将返回的对象强制转换为pgArray包含类型的数组。

更新2

示例改进:

首先,您应该像这样定义您的枚举:

public enum MyEnumLanguage {

    en_US("en_US"),
    de_DE("de_DE");

    private final String code;

    private MyEnumLanguage(String code) {
        this.code = code;
    }

    public String getCode() {
        return code;
    }

    public static MyEnumLanguage getEnumByCode(String code) {
        if(code == null || code.isEmpty()) {
            return null;
        }
        for(MyEnumLanguage e : values()) {
            if(e.getCode().equals(code)) {
                return e;
            }
        }

        return null;
    }
}

然后将您的pgArray映射到List:

Array pgArray = rs.getArray("lang");
String[] langJavaArray = (String[]) pgArray.getArray(); //this returns an Object, so we cast it to a String array

List<MyEnumLanguage> myEnumLanguageList =
        Arrays.stream(langJavaArray)
        .map(MyEnumLanguage::getEnumByCode)
        .collect(Collectors.toList())
;

请注意,映射函数不会检查空值。因此,如果传递错误的代码,则您的列表将包含空值。如果这不是预期结果,则必须在映射函数中执行适当的检查并处理空值情况。

Arrays.asList() 接受一个 Java 语言数组作为参数,它与 java.sql.Array 没有任何相似之处。除此之外,你需要将列表转换为流(stream()),或使用 Arrays.stream()。 - mtj
@mtj 你说得对,我误读了问题并更新了我的答案。至于 stream() 方法,我只是忘记了它! - antonis

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接