我试着看看Array#[]=
是如何运作的,然后玩了:
enum[int] = obj → obj
enum[start, length] = obj → obj
enum[range] = obj → obj
问题1
我有一个数组b
在其nil
索引处持有0
。
b = []
b[0] # => nil
我尝试在下面的代码中将nil
替换为整数10
。
b[-1] = 10 # => IndexError: index -1 too small for array; minimum: 0
为什么上面的代码不起作用,但下面的代码呢?对于大小为1
的数组,为什么索引0
和-1
的处理方式不同?
b[0] = 5 # => 5
b[-1] = 10 # => 10
问题2
我创建了一个大小为2
的数组,并执行了以下操作:
a = [1,2]
a[-3] = 3 # => IndexError: index -3 too small for array; minimum: -2
a[-3] = [3] # => IndexError: index -3 too small for array; minimum: -2
a[-3..-4] = [3] # => RangeError: -3..-4 out of range
我认为负面索引永远不会增加数组的大小,但我不知道为什么。为什么下面的代码成功了?
a[-2..-3] = [3,4] #=> [3, 4]
答案 0 :(得分:7)
我建议你看看Array documentation中的第一段。令人惊讶地说:“假设负索引相对于数组的末尾 - 也就是说,索引-1表示数组的最后一个元素,-2是数组中最后一个元素的下一个元素,因此上“。
这意味着,您可以a[-N]
设置|N| <= a.size
元素。a = [1,2] ; a[-3] = 3
。这就是a[INBOUNDS_IDX..NONSENSE_IDX]=SMTH
失败(3&gt; 2)的原因。
另一方面,[可能]没有记录红宝石阵列的功能:SMTH
将插入 INBOUNDS_IDX
{{1索引:
a=[1,2]
a[2..0]='a'
a[2..1]='b'
a[2..-100]='c'
# ⇒ [1, 2, "c", "b", "a"]
a[2..-1]='q'
# ⇒ [1, 2, "q"]
这里的废话意味着“少于INBOUNDS_IDX,和不能作为否定表示法中的索引处理”(这就是为什么上面示例中的a[2..-1]
被视为a[2..(a.size - 1)]
。)
答案 1 :(得分:0)
观察#1
-1索引与最后一个元素相关,如果数组没有size [],则在使用一个或多个元素初始化之前不能使用它。
观察#2:
是的,你是对的,负数索引永远不会增加数组的大小,如果只引用数组中的具体现有位置。不要认为数组是循环的(0索引符合N-1索引),所以你不能使用任何负面索引认为它是有效的
答案 2 :(得分:0)
<强> Q1:强>
空数组有0个元素,因此当您尝试使用负索引-1
设置其元素0时,它将给出错误。
因为负数索引从数组开始循环。
所以 <{1}}使得无法
a)将元素放在最后位置,因为它为null
b)设定其值。因为它从未被捕获过。
a = []; a[-1] = 3
将起作用,因为您告诉编译器
a)抓住第一个元素,
b)如果不存在则创建一个,然后将其分配给您请求的值。
请参阅official api doc特别提到正索引可以增长大小,负数索引超过数组的开头会引发错误。
<强> Q2:强>
以上解释几乎也回答了第二个问题。
给定a[0] = 5
a = [1,2]
导致第一个休息点。您正尝试从末尾访问第3个元素,该元素不存在。按设计它会崩溃。
虽然a[-3] = 3
在定义的数组的捕获范围内。
你要求解释器捕获最后一个元素(在这种情况下是从前面开始的第一个元素),并尝试调用一个范围,要求它增加数组的大小,并用你要求的任何东西填充它。 / p>
令人高兴的是,一切仍然很好,并且符合要求。很高兴知道。