Java:原始数据类型数组不会自动装箱

发布于 2024-07-12 12:29:26 字数 551 浏览 8 评论 0原文

我有一个这样的方法:

public static <T> boolean isMemberOf(T item, T[] set)
{
    for (T t : set) {
        if (t.equals(item)) {
            return true;
        }
    }
    return false;
}

现在我尝试使用 Tchar 来调用此方法:

char ch = 'a';
char[] chars = new char[] { 'a', 'b', 'c' };
boolean member = isMemberOf(ch, chars);

这不起作用。 我希望 charchar[] 自动装箱为 CharacterCharacter[],但这并没有似乎没有发生。

有什么见解吗?

I have a method like this:

public static <T> boolean isMemberOf(T item, T[] set)
{
    for (T t : set) {
        if (t.equals(item)) {
            return true;
        }
    }
    return false;
}

Now I try to call this method using a char for T:

char ch = 'a';
char[] chars = new char[] { 'a', 'b', 'c' };
boolean member = isMemberOf(ch, chars);

This doesn't work. I would expect the char and char[] to get autoboxed to Character and Character[], but that doesn't seem to happen.

Any insights?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(10

静若繁花 2024-07-19 12:29:26

数组没有自动装箱功能,仅适用于基元。 我相信这是你的问题。

There is no autoboxing for arrays, only for primitives. I believe this is your problem.

や莫失莫忘 2024-07-19 12:29:26

为什么 char[] 会被装箱到 Character[]? 数组始终是引用类型,因此不需要装箱。

此外,它会非常昂贵 - 它将涉及创建一个新数组,然后依次装箱每个字符。 哎呀!

Why would char[] be boxed to Character[]? Arrays are always reference types, so no boxing is required.

Furthermore, it would be hideously expensive - it would involve creating a new array and then boxing each char in turn. Yikes!

滥情空心 2024-07-19 12:29:26

您可以使用反射来获取适用于所有类型数组的方法,但您会失去类型安全性,因此这可能不是您想要的。

import java.lang.reflect.Array
public static boolean isMemberOfArray(Object item, Object array)
{
    int n = Array.getLength(array)
    for (int i = 0; i < n; i++) {
        if (Array.get(array, i).equals(item)) {
            return true;
        }
    }
    return false;
}

You could use reflection to get a method that works for all types of arrays, but you would lose type safety, so this is probably not what you want.

import java.lang.reflect.Array
public static boolean isMemberOfArray(Object item, Object array)
{
    int n = Array.getLength(array)
    for (int i = 0; i < n; i++) {
        if (Array.get(array, i).equals(item)) {
            return true;
        }
    }
    return false;
}
墨洒年华 2024-07-19 12:29:26

正确,数组没有自动装箱(这会导致像 int[] ints; ...; Arrays.asList(ints) 这样的情况出现奇怪的情况 - asList 返回一个包含单个对象的列表,即数组!)

这是一个用于装箱数组的简单实用程序。

public static Integer[] boxedArray(int[] array) {
    Integer[] result = new Integer[array.length];
    for (int i = 0; i < array.length; i++)
        result[i] = array[i];
    return result;
}

当然,每种基本类型都需要不同的版本。

Correct, there is no autoboxing for arrays (which results in weirdness in cases like int[] ints; ...; Arrays.asList(ints) - asList returns a List containing a single Object, the array!)

Here's a simple utility to box an array.

public static Integer[] boxedArray(int[] array) {
    Integer[] result = new Integer[array.length];
    for (int i = 0; i < array.length; i++)
        result[i] = array[i];
    return result;
}

You will need a different version for each primitive type, of course.

酷到爆炸 2024-07-19 12:29:26

这似乎是设计使然,既是为了避免如此昂贵的自动装箱操作,也是因为泛型必须与现有的 Java 字节码向后兼容。

请参阅本文此错误

This appears to be by design, both to avoid such an expensive autoboxing operation, and because generics have to be backwards-compatible with the existing Java bytecode.

See this article and this bug, for example.

夜血缘 2024-07-19 12:29:26

数组是一种低级实现类型。 char[] 将是一个包含两字节字符的连续内存区域。 Character[] 将是具有四个或八字节引用的连续内存区域。 您无法使用 Character[] 来包装 char[]。 然而,List 可以包装 char[]

引用数组通常不是一个好主意,除非您正在编写低级代码。 如果您愿意,您可以编写或获取 java.util.Arrays.asList 的等效项。

Arrays are a low-level implementation type of thing. char[] will be a contiguous area of memory with two-byte chars. Character[] will be a contiguous area of memory with four or eight-byte references. You cannot get a Character[] to wrap a char[]. However a List<Character> could wrap a char[].

Arrays of references are not usually a good idea unless you are writing low-level code. You could, if you wish, write or obtain an equivalent of java.util.Arrays.asList.

維他命╮ 2024-07-19 12:29:26

正如其他人提到的,基元数组没有自动装箱。 如果您想将方法与基元数组一起使用,则需要为每个基元类型提供重载。 这似乎是在类库中执行操作的标准方法。 请参阅 java.util.Arrays,例如。

As others have mentioned, there is no autoboxing for arrays of primitives. If you want to use your method with primitive arrays, you will need to provide an overload for each primitive type. This seems to be the standard way of doing things in the class libraries. See the overloads in java.util.Arrays, for example.

梦罢 2024-07-19 12:29:26

首先,我会尽量避免使用数组,而是使用列表。

数组没有自动装箱,但可变参数有自动装箱。 因此,如果您将您的方法声明为(具有相同的主体):

public static <T> boolean isMemberOf(T item, T ... set)

那么您可以编写

isMemberOf('a', 'a', 'b', 'c');

个人,我更喜欢使用谷歌的番石榴,您可以在其中编写类似的内容

char ch = 'a';
char[] chars = new char[] { 'a', 'b', 'c' };
boolean member = isMemberOf(ch, Chars.asList(chars).toArray(new Character[0]));

您的代码可能只是一个示例,但如果您真的想测试成员资格,请在你可以这样做:

Chars.contains(chars, ch);

or

ImmutableSet.of('a', 'b', 'c').contains('a')

First, I would try to avoid arrays as much as you can, use lists instead.

There is no autoboxing for arrays, but there is autoboxing for varargs. So if you declare your method as (with the same body):

public static <T> boolean isMemberOf(T item, T ... set)

then you can write

isMemberOf('a', 'a', 'b', 'c');

Personally, I prefer using google's guava, where you can write things like

char ch = 'a';
char[] chars = new char[] { 'a', 'b', 'c' };
boolean member = isMemberOf(ch, Chars.asList(chars).toArray(new Character[0]));

Your code was probably just an example, but if you really wanted to test membership, in you can do it like this:

Chars.contains(chars, ch);

or

ImmutableSet.of('a', 'b', 'c').contains('a')
情释 2024-07-19 12:29:26

输入 Java 8 并让 primArrayPrimType[] 类型的标识符,然后您可以执行以下操作:
<代码>
BoxedType[] boxedArray = IntStream.range(0, primArray.length).mapToObj(i -> primArray[i]).toArray(BoxedType[] :: new);

Enter Java 8 and let primArray be an identifier of type PrimType[], then you can do the following:

BoxedType[] boxedArray = IntStream.range(0, primArray.length).mapToObj(i -> primArray[i]).toArray(BoxedType[] :: new);

兔小萌 2024-07-19 12:29:26

一个更简单的方法是

char ch = 'a';
String chars = "abc";
boolean member = chars.indexOf(ch) >= 0;

A simpler way to do this is

char ch = 'a';
String chars = "abc";
boolean member = chars.indexOf(ch) >= 0;
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文