【JavaScript】every、someを空配列に対して実行すると... trueを返す？falseを返す？

## `every` `some`

`every`は、**配列の要素全てが特定の条件に合うかどうか**をチェックするメソッドです。
~~~javascript
const array = [1, 2, 3];

// 配列 array が持つ要素全てが 2 よりも大きいかどうか
const result = array.every((value) => value > 2);

console.log(result); // false
~~~
`some`は、**配列の要素で最低1つが特定の条件に合うかどうか**をチェックするメソッドです。
~~~javascript
const array = [1, 2, 3];

// 配列 array の中に 2 よりも大きい要素はあるかどうか
const result = array.some((value) => value > 2);

console.log(result); // true
~~~

## 空配列に対して実行した場合の挙動

では、**これらのメソッドを、空配列に対して実行した場合はどうなるのでしょうか？**

結論から述べると、**`every`の場合は`true`、`some`の場合は`false`を返します。**
~~~javascript
const arrary = [];

const result = arrary.every((value) => value > 2);

console.log(result); // true
~~~
~~~javascript
const arrary = [];

const result = arrary.some((value) => value > 2);

console.log(result); // false
~~~

これが、今回の記事で伝えたいことです！

このような結果になる理由も面白いので、併せて覚えていただけると幸いです。

## 挙動の解説

`every`、`some`の挙動は、それぞれ「**全称量化子**」と「**存在量化子**」という考え方に基づいています。ややこしそうな言葉なのですが、意外と単純です！<br><br>



全称量化子とは、「**集合内のすべての要素がある条件を満たすか**」を表すものです。

「集合内のすべての要素が条件と合うかチェックする。」というより、「集合内に条件と矛盾している要素が存在するかどうかチェックする。」と考えると分かりやすいと思います。
空の集合には何も存在しないので、もちろん「条件と矛盾している要素」も存在しません。というわけで全称量化子は常に真となる訳です。
これが、空配列に対して`every`を実行した場合に`true`を返す理由になります。<br><br>

存在量化子とは、「**集合内に条件を満たす要素が存在するか**」を表すものです。

集合の中に、条件を満たした要素の**存在**がある時点で、真となります。空の集合には何も存在しないので、もちろん「条件を満たした要素」も存在しません。というわけで存在量化子は常に偽となります。
これが、空配列に対して`some`を実行した場合に`false`を返す理由になります。<br><br>


まとめると、
- 全称量化子は集合内から条件と矛盾した要素を探す。空の集合には矛盾した要素は存在しないので常に真となる。この考え方に基づき、`every`を空配列に対して実行すると`true`を返す
- 存在量化子は条件を満たした要素の存在を探す。空の集合にはいかなる要素も存在しないので常に偽となる。この考え方に基づき、`some`を空配列に対して実行すると`false`を返す。

___

僕が個人的に分かりやすかった例を紹介したいと思います。

空箱を想像してみください...📦

「箱の中に入ったボールが全て赤色ですか？」と聞かれたとします。

その条件と矛盾するボール、つまり赤色以外のボールが無ければ、これは条件を満たしていると言えます。

箱の中身は空です。条件と矛盾するボール、赤色以外のボールはありません！

つまり、「箱の中に入ったボールが全て赤色ですか？」という質問に対しては、「うん！」と答えるのが正しいです。

これが全称量化子な考え方であり、空配列に対して`every`を実行した場合に`true`を返す理由になります。

![Screen Shot 2023-09-14 at 7.19.32.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2356280/cb665030-13a8-a7f7-5299-b0284efc09d7.png)

では次に、「箱の中に赤色のボールはありますか？」と聞かれたとします。

これは文字通り、箱の中に赤色のボールが存在すれば、「うん！」と言えます。

ですが、箱の中身は空なので、もちろん赤色のボールは見つけられません...

つまり、「箱の中に赤色のボールはありますか？」という質問に対しては、「いいえ！」と答えるのが正しいです。

これが存在量化子な考え方であり、空配列に対して`some`を実行した場合に`false`を返す理由になります。

![Screen Shot 2023-09-14 at 7.20.10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2356280/984723a4-a4ca-f04e-eedc-b20b4158e49d.png)


## 他の言語ではどうなる？

今回、JavaScriptの`every`と`some`を挙げましたが、多くの言語にもこれらに相当するメソッド（集合の全ての要素が条件を満たすか、条件を満たす要素が存在するかチェックするメソッド）があります。

全ての言語とは断定できませんが、だいたいのメジャーな言語でも「集合が空の場合、全称量化子に基づくメソッドは`true`を返し、存在量化子に基づくメソッドは`false`を返す」というJavaScript同様の挙動になります。

~~~python:Python ( all / any )
print(all([]))  # True
print(any([]))  # False
~~~
~~~ruby:Ruby ( all / any )
p [].all? { |x| x.even? }  # True
p [].any? { |x| x.even? }  # False
~~~
~~~java:Java ( allMatch / anyMatch )
System.out.println(Arrays.asList().stream().allMatch(x -> (int)x % 2 == 0));  // True
System.out.println(Arrays.asList().stream().anyMatch(x -> (int)x % 2 == 0));  // False
~~~

## まとめ

- 配列が空の場合、`every`は「全称量化子」の考え方に基づき、`true`を返す。
- 配列が空の場合、`some`は「存在量化子」の考え方に基づき、`false`を返す。

最後まで読んでいただき、ありがとうございました✨