HOME»基本情報技術者試験掲示板»平成29年秋  Javaの問題
投稿する

平成29年秋  Javaの問題 [2578]

 ABCさん(No.1) 
お世話になります。

こちらの問題で出てくるcompare()のint型の戻り値(正の数、負の数、0)というのはなんのために使われているのでしょうか?
解説を見てもなんのための処理なのかわかりません。

回答よろしくお願いいたします。
2020.12.21 01:18
メタルさん(No.2) 
FE ブロンズマイスター
過去問のPDF、APIの説明は読まれましたか?
実際の試験でも冊子の後ろの方に書かれています。
以下のURL76ページです。PDFでは77Pになります。
https://www.jitec.ipa.go.jp/1_04hanni_sukiru/mondai_kaitou_2017h29_2/2017h29a_fe_pm_qs.pdf
2020.12.21 07:49
メタルさん(No.3) 
FE ブロンズマイスター
クラスやメソッドは出題者が自作した物が問題文に、元からあるAPIは、冊子の後ろの方に書かれています。
2020.12.21 07:51
 ABCさん(No.4) 
質問する前から読んでいましたが、わかりませんでした。
初めはこのメソッドの戻り値(正の数、負の数、0)を比較してソートするのかと思っていましたが
単純にテーブルの値を比較しているだけのようなので、戻り値の役割がわからなくなってしまいました。

初心者にもわかりやすく解説していただけると助かります。
2020.12.21 17:16
メタルさん(No.5) 
FE ブロンズマイスター
この投稿は投稿者により削除されました。(2020.12.21 22:14)
2020.12.21 22:14
メタルさん(No.6) 
FE ブロンズマイスター
失礼しました。
プログラム1のことですか?
何行目ですか?
2020.12.21 22:15
 ABCさん(No.7) 
プログラム1ではsortメソッドの3行目です。プログラム2にも何箇所かあります。

なぜ何行目か聞いたのか、理由も知りたいです。
2020.12.22 09:38
メタルさん(No.8) 
FE ブロンズマイスター
ABC様、コードの一部がわからないのかと思いましたので、その質問をさせていただきました。
何がわからないのかおおむねわかりました。
しかし、結構説明難しいので週明けまで時間ください。
機能自体は複雑ではないのですが。
2020.12.23 06:03
 ABCさん(No.9) 
ありがとうございます!
回答お待ちしております。
2020.12.23 16:25
メタルさん(No.10) 
FE ブロンズマイスター
おまたせしました。
それでは、まずコアな部分を説明します。
問題文のソースコードを見ながらお読みください。
プログラム1、14行目
Arrays.sortというメソッドが行をソートする機能です、Arrays.sortの内部でcompareが使われ、compareの戻り値を元に表の内容を入れ替えてソートしております。
Arrays.sortの1つ目の引数が表の内容、2つ目の引数がCompareratorのcompareを記述したオブジェクトを渡しています。
Arrays.sortは受け取った1つ目の引数から行を取り出し、2つ目の引数で受け取ったcompareを使い比較する2つの行をcompareの1つ目の引数と2つ目の引数に渡します。
そして帰ってきた値によってどっちが大きいか判断して並べ替えていきます。
解説にも、
o1とo2の大きさが等しいときは0
o1がo2より小さいときは負の値
o1がo2より大きいときは正の値
と書いてある通りこの戻り値で比較する行同士の大小か等しいかを判断しています。
このArrays.sort内部の処理はAPI側で実装されているため、プログラムする側はcompareの処理内容を仕様に沿って書いて渡す部分だけ書きます。
2020.12.25 08:37
メタルさん(No.11) 
FE ブロンズマイスター
プログラム1、14行目から25行目までArrays.sortに引数を渡す処理ですが、
コードがややこしくみえるのは、2番めの引数をインナークラスと呼ばれる記述法で書いてるためです。
これは、Compareratorのcompareメソッドの処理内容を定義すると同時にインスタンス化するという省略したような書き方です。
グーグルなどで"JAVA インナークラス"で検索して調べてみてください。
2020.12.25 08:43
メタルさん(No.12) 
FE ブロンズマイスター
次に全体の処理を、
プログラム2では、最初に表のデータを作り、プログラム2のTableSorterをインスタンス化し、
putSortOrderで表の一列目のソート用の条件を登録、(13行目)
更にputSortOrderで表の二列目のソート用の登録、(18行目)
sorter.sortでプログラム1のTable.sorter内のsortメソッドを実行し、(23行目)
プログラム2の13行目または18行目のputSortOrderで登録したcompareで、
int order = orderMap.get(orderBy.key).compare(s1 [orderBy.col],s2 [orderBy.col]);(実際のコードは改行されていますがこのコードと同じです。)(プログラム1、17行目)
で比較して帰ってきた戻り値を元にプログラム2でsorter.sortを実行したときに渡した、
OrderByメンバのisReversedの値を使って、昇順または降順になるように、戻り値を返す記述をします。
このcompareをArrays.sortに渡しソートします。
プログラム2にある25行目のfor文は単に結果の表示用です。
2020.12.25 09:33
メタルさん(No.13) 
FE ブロンズマイスター
あとインナークラスと言いましたが厳密にはインナークラスの一つ匿名インナークラスなので、
"JAVA 匿名インナークラス"で検索したほうが見つかりやすいかもしれません。
2020.12.25 09:35
メタルさん(No.14) 
FE ブロンズマイスター
要はcompareの戻り値はArrays.sortの内部で使います。
ただし並べ替えの処理自体はArrays.sortの内部でやりますのでプログラマーはcompareの戻り値を書いて
Arrays.sortの引数として渡すだけでいいですよ実際の並べ替えはArrays.sortのAPIがやりますよということです。
この機能でこの問題みたいに柔軟に並べ替えの条件がかけるようになっているわけです。
2020.12.25 09:45
 ABCさん(No.15) 
ご丁寧な解説ありがとうございます

No.10で
>compareの戻り値を元に表の内容を入れ替えてソートしております
とありますが、つまり例えば
compare()の戻り値が1ならば第一引数の方が大きいとsort()が判断して並び替え処理をsort()が行うということでしょうか?

その場合sort()は引数1と引数2を比較する処理を何度も行うことになりますが、比較する行はどのように入れ替わっているのですか?
2020.12.25 15:16
 ABCさん(No.16) 
またNo.12で
>putSortOrderで表の一列目のソート用の条件を登録、更にputSortOrderで表の二列目のソート用の登録
とありますが、一列目、二列目というのはどこに書かれているのでしょうか?

お手数おかけしますが、回答よろしくお願いします。
2020.12.25 15:18
 ABCさん(No.17) 
すみません、追加で質問させてください。

最後の問題(e)で-orderと書くと昇順降順が入れ替わるというのがわかりません。

多分sort()の挙動が分からないからこの辺りが全部わからないのだと思いますが解説していただけると嬉しいです。

また、sort()の処理はAPI側で実装されているとのことですが、なぜAPIの解説にsort()に関するものがないのでしょうか?不親切に感じてしまいました。。。

よろしくお願いいたします。
2020.12.25 15:34
メタルさん(No.18) 
FE ブロンズマイスター
この投稿は投稿者により削除されました。(2020.12.25 20:50)
2020.12.25 20:50
メタルさん(No.19) 
FE ブロンズマイスター
No.15の質問について回答します。
>>compare()の戻り値が1ならば第一引数の方が大きいとsort()が判断して並び替え処理をsort()が行うということでしょうか?

はい、そうです。

>>その場合sort()は引数1と引数2を比較する処理を何度も行うことになりますが、比較する行はどのように入れ替わっているのですか?
イメージとしては以下のようなコードですね。
バブルソートで書いてますが実際のコードだとクイックソートです。

sort(String[][] a,Comparaor c){//引数1プログラム1のtable,引数2プログラム1の15行目のコンペア
  int i, j;
  String[] temp;
  int array_size = a.length;
  for (i = 0; i < (array_size - 1); i++) {
    for (j = (array_size - 1); j > i; j--) {
        if (c.compare(a[j-1] , a[j]) > 0) {//プログラム1の15行目のコンペアを使っている。
        temp = a[j-1];
        a[j-1] = a[j];
        a[j] = temp;
        }
   }
  }
}

String[][] aは2次元配列ですが、a[0]とかで渡すと、aの行が一行、つまり一次元の3列の配列として渡されます。
つまりcompareの引数のString[] s1 に {apple ,3,1000}とかがループごとに入ります。
2020.12.25 20:51
メタルさん(No.20) 
FE ブロンズマイスター
No.16の質問について回答します。

>>とありますが、一列目、二列目というのはどこに書かれているのでしょうか?
確かに一列目用の二列目用の条件ですが、列を指定しているのは後の方ちょうどアルファの矢印でし示されている部分ですね。

問題文の(2)に
フィールド col は比較対象の列の位置を示す数(行を表す String 型配列の添字)である。
と説明があるので、new TableSorter.OrderBy("lex",0)とか  new TableSorter.OrderBy("num",1,true)とか書かれてる2つ目の引数、0と1の部分ですね、ただし配列なので一列目じゃなくて0からし亭されていますね。プログラム1を見ればこれがcolに代入されているので(プログラム1の33行目や37行目)列の指定ですね。
最終的にプログラム1の18行目でcolで使われますね。
2020.12.25 21:10
メタルさん(No.21) 
FE ブロンズマイスター
この投稿は投稿者により削除されました。(2020.12.25 21:37)
2020.12.25 21:37
メタルさん(No.22) 
FE ブロンズマイスター
No.17の質問について回答します。
>>最後の問題(e)で-orderと書くと昇順降順が入れ替わるというのがわかりません。
要は、戻り値がマイナスかゼロかプラスかで判断してるわけです、
その本来の戻り値にマイナス符号をつけると反転するわけです。
-1が帰るところにマイナスを付けると--1=+1に、
+1が帰るところにマイナスを付けると-1に、
0にマイナスを付けると0。
単純に戻り値を反転させると列の先頭から小さい値のものを揃えていた処理が逆になって、先頭から大きいものから順に並べていく処理に反転する理屈なのですが、
混乱するようなら、ソートアルゴリズムの代表的なものグーグルなどで検索して理解してみてください。
バブルソートとかシェルソートとか、マージソートとか、読んで覚えるだけじゃなくて実際にJAVAでコンパイラを使って実装してみたりすると昇順、降順、の並び替えの理屈とかわかると思います。

>>また、sort()の処理はAPI側で実装されているとのことですが、なぜAPIの解説にsort()に関するものがないのでしょうか?不親切に感じてしまいました。。。
一応冊子の76ページに申し訳程度に解説がありますね。
主要機能を覚えてきてからチャレンジしてねってことじゃないですか?
IPAさんがどう考えてるかはわかりませんが。。。
2020.12.25 21:38
メタルさん(No.23) 
FE ブロンズマイスター
んー?ちょっとわかりにくかったかな。
まあ、JAVA言語でプログラム書いたりアルゴリズムの本買って
代表的なアルゴリズム理解すると良いと思います。
JAVA言語の機能は更新され続けるため過去問のAPIが古かったりすることもあるため国試向きではないかもしれません。
どうしても難しそうならCASL2に変える方法もありますし、じっくり取り組んでみてください。
それでは。
2021.01.01 20:14
ABCさん(No.24) 
お返事遅くなり申し訳ありません!
ご丁寧な解説ありがとうございました!!

javaはプログラム言語の問題中でも難しいそうですが、仕事でも使うことになると思うので頑張ってjavaで受験します!
2021.01.04 09:53
メタルさん(No.25) 
FE ブロンズマイスター
頑張ってください。
2021.01.04 18:10
返信投稿用フォームスパム防止のためにスレッド作成日から30日経過したスレッドへの投稿はできません。
© 2010- 基本情報技術者試験ドットコム All Rights Reserved.

Pagetop