ログインしてさらにmixiを楽しもう

コメントを投稿して情報交換!
更新通知を受け取って、最新情報をゲット!

Javaの課題丸投げコミュのソートについて

  • mixiチェック
  • このエントリーをはてなブックマークに追加
先に同じ問題を扱ったトピックはありましたが、若干ソースが違うので、新たにトピックを作成させて頂きました。

“ファイルの中のどの位置(何行何文字目)に単語が出現しているかを調べるプログラムを作る”という問題を改良して、

「出現回数の多い順にプリントされるようにしてください。出現回数が同じものは、単語のコード順(Stringの自然な順序)でプリントします。」

という問題がうまく出来ずに悩んでいます。

私の考えたプログラムは

import java.io.*;
import java.util.*;

class Position2 {
private int lineNo;
private int charNo;

/* コンストラクタ */

public Position2(int lineNo,int charNo) {
this.lineNo = lineNo;
this.charNo = charNo;
}

/* 場所を合わせて文章化 */

public String toString() {
return lineNo+"行"+charNo+"文字目";
}
}

class WordPosition2 {
Map<String,List<Position2>> map=new TreeMap<String,List<Position2>>(new FrequencyComparator());

// キーがString、値がPositionのListであるようなMap型のmapを宣言。
// HashMapをnewして初期化しておく。

public void addWord(String word,Position2 pos) {

// wordがすでにmapに存在するなら、PositionのListにposを追加。
// wordがmapになければ、Listを新しく生成する。

if(map.containsKey(word)){
List list=map.get(word);
list.add(pos);
map.put(word,list);
}
else{
List<Position2> list=new ArrayList<Position2>();
list.add(pos);
map.put(word,list);
}
}

/* 単語と単語のあった場所を出力するメソッド */

public void print() {
Set<String> keys=map.keySet();
Iterator<String> iteratorMapKey=keys.iterator();
while(iteratorMapKey.hasNext()){
String key=iteratorMapKey.next();
System.out.print(key);
Iterator<Position2> iteratorList=map.get(key).iterator();
while(iteratorList.hasNext()){
Position2 pos=iteratorList.next();
System.out.print(" "+pos.toString());
}
System.out.println();
}

}

/*ファイルを一行ごとに読み込むメソッド*/

private void processFile(String fileName) throws IOException {
BufferedReader r = new BufferedReader(new FileReader(fileName));
String line;

// 一行ごとに読み込む

for(int lineNo = 1; (line = r.readLine()) != null; lineNo++) {
processLine(line,lineNo);
}
r.close();
}

/* 行から単語を探すメソッド */

private void processLine(String line,int lineNo) {
int wordStart = -1;
int i = 0;
for ( ; i < line.length(); i++) {
char c = line.charAt(i);
if (isWordChar(c)) { // 単語ならtrue
if (wordStart < 0) {// 単語の始まりなら何文字目か記録
wordStart = i;
}
} else {
if (wordStart >= 0) {//単語の終わりだった場合
addSubstring(line,wordStart,i,lineNo);
wordStart = -1;
}
}
}
if (wordStart >= 0) {// 単語で行数が終わった場合
addSubstring(line,wordStart,i,lineNo);
}
}

/* 単語の場所をPositionに記録、単語とPositionをaddWordに引き渡すメソッド */
private void addSubstring(String line,int start,int end,int lineNo) {
String word = line.substring(start,end);// 単語
Position2 pos = new Position2(lineNo,start + 1);// 単語のあった場所
addWord(word,pos);
}

/* 漢字か片仮名か判定するメソッド */

private boolean isWordChar(char c) {
return isKanji(c) || isKatakana(c);
}

/* 漢字か判定するメソッド */

private boolean isKanji(char c) {
return Character.UnicodeBlock.CJK_UNIFIED_IDEOGRAPHS.equals(
Character.UnicodeBlock.of(c));
}

/* 片仮名か判定するメソッド */

private boolean isKatakana(char c) {
return Character.UnicodeBlock.KATAKANA.equals(
Character.UnicodeBlock.of(c));
}

/* メインメソッド */

public static void main(String[] args) throws IOException {
WordPosition2 wp = new WordPosition2();
wp.processFile(args[0]);
wp.print();
}
}

/* ソート */

class FrequencyComparator implements Comparator<List<Position2>>{
public int compare(List<Position2> l1,List<Position2> l2){
if(l1.size()>l2.size()){
return -1;
}else if(l1.size()==l2.size()){
return 0;
}else{
return 1;
}
}
}

です。

Map<String,List<Position2>> map=new TreeMap<String,List<Position2>>(new FrequencyComparator());

メインメソッドのpublic static void main(String[] args) throws IOException {
が駄目みたいなんですが、これをどう解消したら良いのか分かりません。そもそも、TreeMapでnew FrequencyComparator()とするのがいけないんでしょうか?
どなたかご教授下さい、よろしくお願いいたします!

コメント(4)

FrequencyComparatorについて、問題点が3つあります:

(1)
Comparatorをimplementする際、Comparator<List<Position2>>
というタイプ指定は出来ません。

(2)
前のトピックでも書きましたが、compare()のシグニチャはあくまでも
public int compare (Object o1, Object o2)
である必要があります。

(3)
MapにComparatorを渡す場合、比較されるのはkeyであって、
valueではありません。なので、compare()メソッドを
正しく定義したとしても、送られてくる値は「単語」のStringであって、
「回数」のListにはなりません。

ソートの基準が回数だけであるなら、Collections.sort()に
Listを渡してやればいいですが、この課題では単語自体の
比較も検討しないといけません。

それで、前のトピックでは、Map.EntryをList化してComparatorに
渡したわけです。これなら、compare()の中でkeyとvalue、
両方に手が届きますから。

ログインすると、みんなのコメントがもっと見れるよ

mixiユーザー
ログインしてコメントしよう!

Javaの課題丸投げ 更新情報

Javaの課題丸投げのメンバーはこんなコミュニティにも参加しています

星印の数は、共通して参加しているメンバーが多いほど増えます。

人気コミュニティランキング