ary[-1]の動作
ary[-1]の動作
配列の-1番目の要素を指定した場合何が起こるのかちょっと興味あったので調べてみた
Rubyの場合
ary = [1,2,3] puts ary[-1] # 3
ところで
ary = 1..3 puts ary[-1] # 1..0
になるのは何故でしょうかね。Ruby良く分かりません…
Cの場合
未定義動作ですね
#include <stdio.h> int main(void) { int* ary[] = {1,2,3}; printf("%d\n", ary[-1]); // 4195648 return 0; }
C++のVectorの場合
やはり未定義動作のようです。ちなみにC++11。
#include <iostream> #include <vector> int main() { std::vector<int> v = {1, 2, 3}; std::cout << v[-1] << std::endl; // 0 return 0; }
Javaの場合
例外が飛んできますね。
import java.util.Arrays; import java.util.List; public class Main { public static void main(final String[] args) { int[] ary1 = { 1, 2, 3 }; List<Integer> ary2 = Arrays.asList(1, 2, 3); System.out.println(ary1[-1]); // java.lang.ArrayIndexOutOfBoundsException System.out.println(ary2.get(-1)); // java.lang.ArrayIndexOutOfBoundsException } }
Groovyの場合
残念なJavaに脅威の魔科学を投入することで恐しいことになっているGroovyは、Python・Rubyと同じ挙動
def ary1 = [1,2,3] def ary2 = Arrays.asList(1,2,3) println ary1[-1] // 3 println ary2[-1] // 3
Haskellの場合
Exceptionが飛んでくる模様
Prelude> let ary = [1,2,3] Prelude> ary !! (-1) -- Exception: Prelude.(!!): negative index
D言語の場合
Range violationだそうで。
import std.stdio; void main() { int[] ary = [1,2,3]; writeln(ary[-1]); // Range violation }
結論
- 古典的な言語は-1で範囲外参照する
- スクリプト言語は一番後ろの値を持ってくる
- 最近の静的型付け言語は例外を投げる