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

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

新規登録して質問してみよう
ただいま回答率
85.48%
Collections API

Collections APIは開発者に複数のクラスやインターフェイスを供給し、多くのオブジェクトを扱いやすくします。

Java

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

Q&A

解決済

1回答

3005閲覧

ListのCollections.sortで、ソートをしたいが、listの読み込みが正しく出来ない。

Y.Mamoru

総合スコア47

Collections API

Collections APIは開発者に複数のクラスやインターフェイスを供給し、多くのオブジェクトを扱いやすくします。

Java

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

0グッド

0クリップ

投稿2020/08/18 02:33

○やりたいこと
社員名簿アプリを作成しています。「社員番号,名前,部署」の3要素をMapで保存し、そのとき「社員番号」のKeyListと、「名前、部署」のValueListを格納するように作っています。
格納・一覧・変更・消去機能は正常に動きます。
やりたいことは、社員番号をランダムに登録した後でも、昇順にソートできるようにしたいです。

○困っている事
Collections.sortをかけても社員番号Listがソートされません。
原因を探っていると、私の考えでは
・複数の値を登録してもKey.size()が1になっている。このことからKeyListには値が1つしか登録されていない。だからソートされない。(そもそも1つだから。)と考えています。
しかし一覧表示の際には、各要素が正しく表示されているので、なぜKeysize()が1になるかの理由もわかっていません。

ソートはコード内の★★★を付けている部分です。
助言をお願いします。

Java

1package Java_IO; 2 3import java.util.ArrayList; 4import java.util.Arrays; 5import java.util.Collections; 6import java.util.LinkedHashMap; 7import java.util.List; 8import java.util.Map; 9import java.util.Scanner; 10 11public class IO_Task_6 { 12 public static void main(String[] main){ 13 //各種定義 14 List<String> key = new ArrayList<String>(); //key用のlist 15 16 Map<List<String> , ArrayList<String>> map = new LinkedHashMap<List<String> , ArrayList<String>>();//mapの定義 17 String str; //入力された文字列情報として扱う 18 String[] info; //入力された3つの情報をわけて配列として扱う時に使う 19 String[] array; //配列収納用 20 21 //標準入力 22 Scanner scan = new Scanner(System.in); 23 24 25 while(true){ 26 //指示文 27 System.out.println("コマンドを入力して下さい。(-i:新規追加 , -u:変更 , -d:消去 , -v:一覧 , -s:ソート , -e:終了 , -m:モード選択)"); 28 String command = scan.nextLine(); 29 30 //switch文で切り替え 31 switch(command){ 32 //-i(新規追加) 33 case"-i"://","で区切って情報を3つ(社員番号・名前・部署)を入力。社員番号をkeyに残り2つをlistでまとめてMAPに代入 34 //繰り返し入力 35 while(true){ 36 //指示文 37 System.out.println("「社員番号 , 名前 , 部署」の順で入力しなさい"); 38 //新規追加情報の入力 39 str = scan.nextLine(); 40 //-mかどうかの確認 41 if(!"-m".equals(str)){ 42 //入力された文字を3つに分ける(配列に変換) 43 info = str.split("," , 0); 44 //info[]が3要素あれば進む。なければ注意文からのもう一度入力 45 if(info.length == 3){ 46 //社員番号の重複確認 47 if(map.get(Arrays.asList(info[0])) == null){ 48 //社員番号配列をlistに変換 49 key = Arrays.asList(info[0]); 50 //listに名前と部署を格納 51 ArrayList<String> arlist = new ArrayList<String>(); //値用のlist 52 arlist.add(info[1]); 53 arlist.add(info[2]); 54 55 //mapに社員番号とlistを格納 56 map.put(key , arlist); 57 System.out.println("登録しました"); 58 break; 59 }else{ 60 System.out.println("入力した社員番号はすでに登録されています。"); 61 }break; 62 }else{ 63 System.out.println("「社員番号 , 名前 , 部署」で入力して下さい"); 64 continue; 65 } 66 } 67 } 68 break; 69 70 71 //-u(変更) 72 case"-u"://社員番号でデータを抽出してからになるかな。 73 //指示文 74 System.out.println("該当する社員番号を入力して下さい"); 75 String num = scan.nextLine(); 76 //-mかどうか確認 77 if(!"-m".equals(num)){ 78 String[] hoge = num.split("," , 0); 79 List<String> hogehoge = Arrays.asList(hoge); 80 //値があるかどうかの確認 81 if(map.get(hogehoge) != null){ 82 //入力された番号からあてはまる値をmapから取得 83 ArrayList<String> arlist = map.get(hogehoge); 84 array = arlist.toArray(new String[0]); 85 //該当情報を表示 86 System.out.println("該当者は、社員番号:" + num + ",名前:" + array[0] + ",部署:" + array[1] + "ですね。"); 87 88 //指示文2 89 System.out.println("新たに「名前 , 部署」を入力して下さい"); 90 str = scan.nextLine(); 91 92 String[] new_info = str.split("," , 0); 93 //古い情報の消去 94 arlist.clear(); 95 //新しい情報をlistに格納 96 arlist.add(new_info[0]); 97 arlist.add(new_info[1]); 98 99 // String[] num_1 = {num}; 100 // List<String> list_1 = Arrays.asList(num_1); 101 102 //mapに上書き格納 103 map.put(hogehoge , arlist); 104 System.out.println("変更登録が完了しました"); 105 }else{ 106 System.out.println("その番号の社員はいません"); 107 } 108 } 109 break; 110 111 112 //-d(消去) 113 case"-d"://社員番号を指定して、消去に持っていく 114 //指示文 115 System.out.println("該当する社員番号を入力して下さい"); 116 num = scan.nextLine(); 117 //-mかどうか確認 118 if(!"-m".equals(num)){ 119 String[] fuga = num.split("," , 0); 120 List<String> fugafuga = Arrays.asList(fuga); 121 //該当する人がいるかどうか確認 122 if(map.get(fugafuga) != null){ 123 //入力された番号からあてはまる値をmapから取得 124 ArrayList<String> arlist = map.get(fugafuga); 125 array = arlist.toArray(new String[0]); 126 //該当情報を表示 127 System.out.println("該当者は、社員番号:" + num + ",名前:" + array[0] + ",部署:" + array[1] + "ですね。"); 128 //消去の意思確認(if分岐を始める) 129 System.out.println("本当に消去してもよろしいですか?「yes」または「no」を入力して下さい"); 130 str = scan.nextLine(); 131 if(str.equals("yes")){ 132 map.remove(fugafuga); 133 System.out.println("社員番号" + num + "のデータを消去しました。"); 134 }else{ 135 System.out.println("データの消去を実行せず終了します。"); 136 } 137 }else{ 138 System.out.println("その番号の社員はいません"); 139 } 140 } 141 break; 142 143 144 //-v(一覧表示) 145 case"-v"://ループで有る分全て表示 146 System.out.println("現在登録されている社員一覧です"); 147 for(List<String> key_ex : map.keySet()){ 148 ArrayList<String> arlist = map.get(key_ex); 149 150 array = arlist.toArray(new String[0]); 151 System.out.println("社員番号:" + key_ex + ",名前:" + array[0] + ",部署:" + array[1]); 152 } 153 154 break; 155 156 157 //-s(ソート) 158 case"-s"://上の一覧表示をもとにして、社員番号でソート 159 Collections.sort(key); //★★★ 160 System.out.println(key); //ここでkeylistの中身を確認すると、複数登録した要素のうちの最後に登録されたものだけが表示されます。 161 System.out.println(key.size()); //ここでkeysize()を確認すると、1と表示されます。 162 163 System.out.println("社員番号でソートが完了しました"); 164 break; 165 166 167 //-e(終了) 168 case"-e"://System.out.exit(0)でOKでしょう。 169 System.out.println("終了します"); 170 System.exit(0); 171 scan.close(); 172 break; 173 174 case"-m": 175 break; 176 177 default: 178 System.out.println("[-i:新規追加 , -u:変更 , -d:消去 , -v:一覧 , -s:ソート , -e:終了]の中から選んでください"); 179 break; 180 181 } 182 } 183 } 184}

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

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

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

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

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

dodox86

2020/08/18 03:02

ソート部分は > Collections.sort(key); ですが、そのkey自体は、case "-i":の部分で key = Arrays.asList(info[0]); とのように、1つだけしかセットしていないように見えます。"-v"の一覧表示の際にはkeyそのものではなく、別のものを見ているので、 > for(List<String> key_ex : map.keySet()){ > ArrayList<String> arlist = map.get(key_ex); 結果が異なっていても仕方が無さそうに思います。 具体的にどういう手順(入力)を行ったらどういう結果となる(出力)を示すと、より適切な回答をいただけると思います。今のご質問内容ではコードが長いので回答者が実際に動かして入力と出力を試行錯誤する必要があります。
yureighost

2020/08/18 05:11

一通り動作確認して試したところの感想ですが、今の処理を見る限りでは、 -v(一覧表示)で登録した物が社員番号順に並んで欲しいのだと思います。 そうだとするとソートすべきなのはmapの方です。 そもそもkeyには一つしかキーが入らないようなのでソートしようがありません。 そうなるとLinkedHashMapクラスを使っているのは不適です。 このクラスは追加した順番で処理することを保証するMapクラスです。 キーでソートすることを想定しているならTreeMapを使うべきです。 キー部分にListを使わず、TreeMapを使っているなら引数無指定の宣言で自然順序付けで並ぶのが保証されます。 本当にキー部分にListクラスが必要なのかを含めて再検討することをお勧めします。
Y.Mamoru

2020/08/18 08:42

@dodox 確かに全文を書くのはよくなかったですね。次回に気を付けます。 また参照先が違うという話、納得できました。 ありがとうございます。 @yureighost 全文読んで下さったのですね。ありがとうございます。 言って頂いた通りLinkedHashMapからTreeに変更し、キー部分を文字列に変更する事で正常に動かすことが出来ました。 ありがとうございます。
guest

回答1

0

ベストアンサー

key=の所で毎回新しくしてますね、listの更新はmapと同じaddですよ(多分)

投稿2020/08/18 03:57

snowshink

総合スコア138

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

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

ironya

2020/08/18 07:14

java.util.Map で追加するときは put です。念のため。。。
Y.Mamoru

2020/08/18 08:44

ありがとうございます。 確かにListとMapの追加はPushですね。 キー部分にpushをするようにつくってみたところ、私がもともとつくっていた他のコードをと合わなくなってしまい、(恐らくうまく出来る方法がある筈なんですが、) 今回はキーの型を変更させることで落ち着きました。 ありがとうございました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

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

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

質問する

関連した質問