72 lines
2.0 KiB
Markdown
72 lines
2.0 KiB
Markdown
# Array Expression
|
|
|
|
array expression は、順序付きの値の列を表す。
|
|
|
|
```dcdl
|
|
[1, 2, 3]
|
|
["a", "b", "c"]
|
|
```
|
|
|
|
配列リテラルは concrete value であり、要素型を揃える必要はない。
|
|
|
|
```dcdl
|
|
["api", 8080, true]
|
|
```
|
|
|
|
## Array constraint
|
|
|
|
配列制約は `[` の直後に ellipsis を置き、その後へ要素制約を記述する。
|
|
|
|
```dcdl
|
|
Names = [...String];
|
|
Ports = [...(Int & >= 1 & <= 65535)];
|
|
```
|
|
|
|
`[...T]` は、すべての要素が `T` を満たす長さ 0 以上の配列を表す。
|
|
空配列は任意の配列制約を満たす。
|
|
|
|
```dcdl
|
|
[...String] & []
|
|
[...String] & ["api", "worker"]
|
|
```
|
|
|
|
要素制約は object range にもできる。
|
|
右辺だけにある default 付き field は、配列へ制約を合成した時点では abstract のまま各要素に残る。
|
|
その配列を後から materialize した場合にだけ default が使われる。
|
|
|
|
```dcdl
|
|
Services = [...{
|
|
name = String;
|
|
enabled = Bool default true;
|
|
}];
|
|
|
|
Services & [{ name = "api"; }]
|
|
```
|
|
|
|
配列制約を concrete array に適用すると、各要素は要素 range に対して `as` と同じ規則で絞り込まれる。
|
|
object の要素 range では左辺にしかない field がエラーになり、右辺にしかない field は abstract のまま残る。
|
|
|
|
要素制約のない抽象配列型は提供しない。
|
|
旧来の `Array` primitive type は使用できず、`[...T]` の `T` は必須である。
|
|
`[String]` は配列制約ではなく、未解決の `String` 制約を 1 要素に持つ concrete array になる。
|
|
配列制約は要素範囲だけを表す。長さ制約、位置別の tuple 制約、unique 制約は持たない。
|
|
|
|
## Array concat
|
|
|
|
`++` は concrete array 同士を連結する。
|
|
|
|
```dcdl
|
|
base = ["read", "write"];
|
|
extra = ["admin"];
|
|
roles = base ++ extra;
|
|
```
|
|
|
|
`roles` は以下と同じ値になる。
|
|
|
|
```dcdl
|
|
["read", "write", "admin"]
|
|
```
|
|
|
|
`++` は配列要素を変換しない。
|
|
左辺の要素の後に右辺の要素が並ぶ。
|