obj1.atcoderには空配列[]が代入されていますので、これ自体は配列、つまり、Arrayオブジェクトです。Arrayオブジェクトは通常オブジェクト(ordinary object)は異なる性質を持ちます(このようなオブジェクトをexotic objectと言います)。Arrayオブジェクト特有の性質の次のようなものです。
lengthプロパティを持ちます。その値は0以上2^32より小さい整数です。
- プロパティ名が0から2^32-1の整数値と等しくなる文字列はarray indexといわれ、特別な扱いとされ、整数値のように処理されます。
lengthはarray indexより必ず大きくなります。
- プロパティへの代入によって最大のarray indexが変更されるとき、
lengthもまた変更されます。
lengthへの代入によって、範囲に収まらないarray indexがあるとき、length以上のarray indexは全て削除されます
- その他に、Arrayオブジェクトの組込インスタンスメソッドのほとんどは(必要があれば)
lengthも一緒に変更します。
プロパティ名としてのarray indexは文字列であることに注意してください。しかし、上記の性質を素早く実現するために、内部では符号無し32bit整数値(numberではありません)として実装されている場合があります。
さて、JavaScriptについてもう一つ重要なことはオブジェクトのプロパティ名は文字列またはシンボルであるということです。それ以外をプロパティ名として使用しようとしても、文字列に変換してから解釈されます。つまり、a[1]とa['1']は同じです。aが配列であってもそれが変わることはありません。
ということでobj1.atcoder['200'] = 'url';はobj1.atcoder[200] = 'url';と同じです。さらにここでobj1.atcoderがArrayオブジェクトであるが故の性質が表れます。'200'はarray indexとして200と解釈され、lengthが201になるということです。
ここでfor (let i = 0; i < a.length; i++) {}やfor (let v of a) {}のような表現でループを回した場合、あたかも0から200までのインデックスがあるかのように振る舞うでしょう。なぜなら、これらは0からlength - 1までループするからです。実際にプロパティがあるのかは関係ありません。
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。