Java | 等幅のコンソールで文字列を一定の長さで出力

Java | 等幅のコンソールで文字列を一定の長さで出力

メンバ変数をいくつか持つクラスの配列・List があった時に、そのデータを 1行ずつ表示させていたのですが、文字列や数値の表示幅を固定して、表みたいに表示できたら見やすいなーと思い、作ってみました。
最初、printf で「最大桁数」と「最小桁数」の指定ができるので、それで行けるかと思いましたが、Java は内部で文字列を Unicode として扱っているので、半角文字も全角文字も 1 文字として扱われてしまい、等幅のコンソールに表示するとズレてしまいます (^^;
ググってみたところ、一回 Shift_JIS にしてから やるという方法もありましたが、それだと一部の文字が使えなくなってしまいます (^^;
そこで、Unicode のコードのまま全角・半角を判定し、出力することにしました!

//
// Main クラス
//
public class Main {

//
// main メソッド
//
public static void main(String[] args) {

// 文字列と長さ 指定
String[] str = {"Ruby ルビー", "サフィー Sapphie", "Garnet ガーネット", "ペリドット Peridot"};
int len = 11;

// printf だと上手くいかない
System.out.println("■printf だと上手くいかない");
for (String s: str) {

System.out.print("[");

// 文字数の最大・最少を len にする
System.out.printf("%-" + len + "." + len +  "s", s);

System.out.println("]");

}

System.out.println();

// 文字幅をちゃんと判定
System.out.println("■文字幅をちゃんと判定");
for (String s: str) {

System.out.print("[");

// 半角 len 文字分の幅で文字列出力
printn(s, len);

System.out.println("]");

}

}

//
// 半角 len 文字分の幅で文字列出力
//
static void printn(String s, int len) {

int l = 0;

// 1 文字ずつ出力
for (int i = 0; i < s.length(); i++) {

char c = s.charAt(i);

//  ( 英数字      )    ( \ 記号      )    ( ~ 記号      )    ( 半角カナ                     )
if ((c <= '\u007e') || (c == '\u00a5') || (c == '\u203e') || (c >= '\uff61' && c <= '\uff9f')) {
l++;
if (l > len) {
l--;
break;
}
} else { // その他 (全角)
l += 2;
if (l > len) {
l -= 2;
break;
}
}

System.out.print(c);

}

// 長さが足りなかった場合は半角スペースで埋める
if (l < len) {
System.out.printf("%" + (len - l) + "s", "");
}

}

}

文字列が短すぎる場合 … スペースで埋める
文字列が長すぎる場合 … 途中で切る。ただし、全角文字がハミ出した場合は半角スペースで調整

ここでは単純に 1 文字ずつ次から次へと print していますが、一回 String に組み立ててから出力するほうが良いかもですね (^^;
あと、文字列が長すぎる場合に、3 つの点「...」を表示するようにするのも面白いかもしれませんね。
最近いろいろ忙しくて役 2 ヶ月ぶりの更新となってしまいましたが、今後もブログは続けていく予定です (^^;
ではまたいつか~。
↓ブログランキング投票 (クリック) お願いします~