Java中的数组索引可以是负数吗?

5
public static void main(String[] args) {
    int[] a = new int[10];
    a[1] =2;
    a[-1] = -2;
    a[0] = 0;
    System.out.println(a[-1]);

}

我在编辑器中编写了代码,编辑器并未判定为非法,但是当我运行它时,会出现以下错误:"Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: -1"

那么,在Java中,负数索引总是非法的吗?还是有某些特殊情况可以使数组的索引成为负数?


1
Java 数组不能有负索引。 - Sharon Ben Asher
使用 Map<Integer, Integer> 然后... - buræquete
编辑器只是一个助手,不是裁判。编译器才是裁判 :) - Tomasz
1
到目前为止已经有八个回答,都是说同样的事情。有多少种方式可以表达“不”? - Joakim Danielson
不,负索引是不可能的,但如果您告诉我们具体问题,我们可以解决您的问题。 - Null Pointer
8个回答

5
让我们看一下 Oracle 的文档 这里。它的内容如下:

数组对象包含多个变量。变量的数量可能为零,在这种情况下,该数组被称为空数组。包含在数组中的变量没有名称;相反,它们是由使用非负整数索引值的数组访问表达式引用的。这些变量称为数组的组成部分。如果一个数组有 n 个组成部分,我们说 n 是数组的长度;可以使用从 0 到 n - 1 的整数索引引用数组的组成部分。

同时,

所有数组访问都在运行时进行检查;尝试使用小于零或大于等于数组长度的索引会导致抛出 ArrayIndexOutOfBoundsException 异常。

回答问题,否,索引不能是负数。


3

Java不支持负数下标,可以通过以下方式访问最后一个元素:

list.get(list.size() - 1);
array[array.length-1] = lastElement;

1
简而言之,不能为负数。
docs(例如使用get):

如果指定的索引参数为负数或大于或等于指定数组的长度,则会抛出ArrayIndexOutOfBoundsException异常


1

在Java中,负数索引始终是非法的吗?

是的。

还是有一些特殊情况可以让数组的索引成为负数吗?

您可以编写自己的类似数组的集合类型,其中负索引将是有效的。这将是一种特定于域的类型,因为我想不出任何一般应用程序。

一个简单的例子是

// define an anonymous class that overrides ArrayList's get behaviour
List<String> list = new ArrayList<String>() {
    @Override
    public String get(int index) {
        return super.get(Math.abs(index));
    }
};

list.add("a");
list.add("b");

System.out.println(list.get(-1)); // b
System.out.println(list.get(1));  // b

我不建议你这么做。对于任何Java开发者来说,这都是令人困惑和不寻常的。


0
正如@Darshan Mehta的回答所说,不允许使用负数作为数组索引。但是,您可以编写自己的数组类,允许使用负索引。
以下是我使用泛型的示例。
public class ModuloArray<E> {
    int size;
    E[] array;

    public ModuloArray(int size) {
        if (size <= 0)
            throw new RuntimeException("not positive");
        
        this.size = size;
        array = (E[]) new Object[size];
    }
    
    public ModuloArray(E... elements) {
        if (elements == null)
            throw new RuntimeException("null");
        
        this.size = elements.length;
        array = elements;
    }

    public E get(int index) {
        return array[Math.floorMod(index, size)];
    }
    
    public void set(int index, E element) {
        array[Math.floorMod(index, size)] = element;
    }
}

public class Main {
    public static void main(String[] args) {
        System.out.println("*** ModuloArray with first constructor ***");
        ModuloArray<String> myArray = new ModuloArray<>(3);
        myArray.set(-1, "apple");
        myArray.set(-2, "orange");
        myArray.set(-3, "banana");
        
        System.out.println(myArray.get(-3));
        System.out.println(myArray.get(-2));
        System.out.println(myArray.get(-1));
        System.out.println(myArray.get(0));
        System.out.println(myArray.get(1));
        System.out.println(myArray.get(2));
        
        System.out.println();
        System.out.println("*** ModuloArray with second constructor ***");
        ModuloArray<String> myArray2 = new ModuloArray<>("glazed donut", "chicken burger", "apple soda");
        
        System.out.println(myArray2.get(-2));
        System.out.println(myArray2.get(3));
    }
}

上面的例子输出:

*** ModuloArray with first constructor ***
banana
orange
apple
banana
orange
apple

*** ModuloArray with second constructor ***
chicken burger
glazed donut

Java中的数组索引仅在条件0 <= index < array.length为真时才有效。但是,因为ModuloArray使用Math.floorMod(int x, int y)来访问数组元素,因此任何整数(包括负数)都可以用作有效索引。这种行为类似于Python中列表的索引工作方式。 enter image description here

0
在Java中,不能使用负索引。它是基于0的正索引。如果使用负索引,则Java会抛出“ArrayIndexOutOfBoundsException”异常。

0
Java中的数组不能使用负数作为索引,问题在于Java中尚未定义无符号整数,因此只要x是有效的数字索引,编写myArr[x]就会编译。

0

简短回答:不行。

稍微长一点的回答:数组索引范围从0到数组长度减1。

例如:

int[] ints = new int[5];
ints[0] = 1;  // fine
ints[4] = 1;  // fine
ints[-1] = 1;  // ArrayIndexOutOfBoundsException thrown
ints[5] = 1;  // ArrayIndexOutOfBoundsException thrown

大多数评论和答案都指向同一个问题,即您无法直接访问负索引,并且会收到ArrayIndexOutOfBoundsException异常。但是,由于负索引意味着以相反的顺序在数组中移动,因此我建议接受@Diya提供的答案作为解决方案。 - CallOfVoid

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