質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.49%
Java

Javaは、1995年にサン・マイクロシステムズが開発したプログラミング言語です。表記法はC言語に似ていますが、既存のプログラミング言語の短所を踏まえていちから設計されており、最初からオブジェクト指向性を備えてデザインされています。セキュリティ面が強力であることや、ネットワーク環境での利用に向いていることが特徴です。Javaで作られたソフトウェアは基本的にいかなるプラットフォームでも作動します。

Q&A

解決済

4回答

2412閲覧

多次元配列のforeach文の動きについて

sobue

総合スコア329

Java

Javaは、1995年にサン・マイクロシステムズが開発したプログラミング言語です。表記法はC言語に似ていますが、既存のプログラミング言語の短所を踏まえていちから設計されており、最初からオブジェクト指向性を備えてデザインされています。セキュリティ面が強力であることや、ネットワーク環境での利用に向いていることが特徴です。Javaで作られたソフトウェアは基本的にいかなるプラットフォームでも作動します。

0グッド

0クリップ

投稿2016/05/19 13:25

java

1 2public class Arrayx3 { 3 4 public static void main(String[] args) { 5 6 //3次元配列の宣言 7 int a3[][][] = new int[3][3][3]; 8 9 for(int i = 0;i < 3;i++){ 10 for(int j = 0;j < 3;j++){ 11 for(int k = 0;k < 3;k++){ 12 a3[i][j][k] = i * 9 + j * 3 + k; 13 } 14 } 15 } 16 17 for(int [][] e1 : a3){ 18 for(int [] e2 : e1){ 19 for(int e3 : e2){ 20 System.out.printf(e3 + " "); 21 System.out.printf(" "); 22 } 23 System.out.println(); 24 } 25 } 26 } 27 28} 29

上記のコードを実行すると
0 1 2
3 4 5
6 7 8
9 10 11
12 13 14
15 16 17
18 19 20
21 22 23
24 25 26
と出ますが
for(int [][] e1 : a3){
for(int [] e2 : e1){
System.out.printf(e2 + " ");
System.out.printf(" ");
System.out.println();
}
}
}
と変更すると
[I@14ae5a5
[I@7f31245a
[I@6d6f6e28
[I@135fbaa4
[I@45ee12a7
[I@330bedb4
[I@2503dbd3
[I@4b67cf4d
[I@7ea987ac
と出ます。
この出力が何を表しているのでしょうか?
メモリの位置なのかな?とも思いましたが・・・・
デバッグをしても綺麗な数字しか表示されないので
よろしくお願いします。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答4

0

配列オブジェクトをそのままprintした場合、このような文字列が出力される仕様になっています。
[Iの部分がint配列という意味を、@の後ろがそのオブジェクトのハッシュ・コードを表しています。

...

java.util.ArraysクラスのtoStringメソッドを使うと、配列の内容を文字列にしてくれます。

  • 使用例

lang

1// import java.util.Arrays; 2System.out.println(Arrays.toString(e2));

java.util.Arraysクラス toStringメソッド - Java SE 8 API ドキュメント
https://docs.oracle.com/javase/jp/8/docs/api/java/util/Arrays.html#toString-int:A-

投稿2016/05/19 13:35

argius

総合スコア9388

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

sobue

2016/05/20 00:05

わかったような…わからないような…。まだ、この動きを知るのには早かったようです。もっと勉強してから再度この回答を見直してみます。ありがとうございます。
guest

0

配列を文字列化しているだけです。

foreachの動きは同じ動きをする通常for文を作ればわかりやすいかも
もともとのコードを直すと次のようになります(一部省略してあります。以下同)

java

1for (int i = 0; i < 3; i++) { 2 int[][] e1 = a3[i]; 3 for (int j = 0; j < 3; j++) { 4 int[] e2 = e1[j]; 5 for (int k = 0; k < 3; k++) { 6 int e3 = e2[k]; 7 System.out.println(e3); 8 } 9 } 10}

で、質問に書かれているコードの方は

java

1for (int i = 0; i < 3; i++) { 2 int[][] e1 = a3[i]; 3 for (int j = 0; j < 3; j++) { 4 int[] e2 = e1[j]; 5 System.out.println(e2); 6 } 7} 8

となり、つまり、最初の[I@14ae5a5の部分は

java

1int[] e2=a3[0][0]; 2System.out.println(e2);

です。
[]の数が混乱するかもしれませんね。
(それを防ぐためでもあるforeach)

現在は通常の配列をprintlnしているだけです。

基本的に配列もオブジェクトです。

ということで
java.lang.ObjectのtoString()が採用されます。
で、java.lang.ObjectのtoStringのドキュメントは

オブジェクトの文字列表現を返します。一般に、toStringメソッドは、このオブジェクトを「テキストで表す」文字列を返します。この結果は、人間が読める簡潔で有益な情報であるべきです。すべてのサブクラスで、このメソッドをオーバーライドすることをお薦めします。
クラスObjectのtoStringメソッドは、オブジェクトがインスタンスになっている元のクラスの名前、アットマーク文字「@」、およびオブジェクトのハッシュ・コードの符号なし16進数表現から構成される文字列を返します。つまり、このメソッドは次の値と等しい文字列を返します。

getClass().getName() + '@' + Integer.toHexString(hashCode())

ソース元(https://docs.oracle.com/javase/jp/8/docs/api/java/lang/Object.html#toString--)

以下を実行してみてください。

java

1public class TruthOfArray { 2 3 public static void main(String[] args) { 4 int[] a = new int[3]; 5 System.out.println(a.getClass()); 6 System.out.println(Integer.toHexString(a.hashCode())); 7 8 System.out.println(a); 9 10 if (a instanceof Object) { 11 System.out.println("配列はオブジェクトだった"); 12 } else { 13 System.out.println("配列はオブジェクトじゃない"); 14 } 15 } 16 17} 18

つまり、配列はオブジェクトで、
クラス名は、「[I」、
オブジェクトのtoStringは「クラス名+@+ハッシュ
よって、配列のtoStringは「[I+@+ハッシュ

実験のためにもe1,e2,e3をSystem.out.printlnしてみてください。

投稿2016/05/20 04:57

編集2016/05/20 05:02
RyotaKondo

総合スコア94

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

ベストアンサー

System.outはPrintStreamオブジェクトであり、このクラスのprint,printlnメソッドは、様々なオーバーロードがあります。プリミティブ値各種とchar配列、String、そしてObjectを受け取り、対応する文字列を出力します。Object(char配列、Stringを除く参照型すべて)を受け取った場合、そのObjectがnullでないかぎり、Object.toString()を呼び出した結果を出力します。char以外の配列も参照型なので、Objectに該当します。
通常、このtoString()メソッドは各種クラスでオーバーライドされ、そのオブジェクトを端的に表す文字列を返すよう設計されるのですが、配列はそうはなっていません。そのため、デフォルトのクラス名@ハッシュコードという形の文字列を返します。配列の場合、クラス名が特殊な形で表されます。

投稿2016/05/19 14:28

swordone

総合スコア20649

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

sobue

2016/05/20 00:04

わかったような…わからないような…。まだ、この動きを知るのには早かったようです。もっと勉強してから再度この回答を見直してみます。ありがとうございます。
guest

0

変数e2はどのような型?そしてこれをprintfメソッドの引数とすると?

投稿2016/05/19 13:34

HogeAnimalLover

総合スコア4830

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

sobue

2016/05/19 13:50

e2は1次元配列ですが?引数に渡すと・・・・?String型で待っているから型がおかしいってことですか?
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.49%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問