[ Excel_Tipe29 へ戻る ]
( Coloring by SyntaxHighlighter )
Tips29: JavaScript で電話番号(局番)の検証/編集 [ ソースファイル ダウンロード ] [ JAVA 用 テストツール ]
[ JavaScript with JSON ( AreaCode4JSON.json ) ]
[ JavaScript ]
[ JAVA ]
[ PHP ]
[ Perl ]
[ Python ]
[ Ruby ]
[ VBA / VB6 ]
[ VB.net ]
( Source Code : JAVA Ver 1.00 )
動作確認環境 [ Eclipse / JAVA 8u192 ] 番号翻訳テーブル [ 2022/7/1 版 ]
//-【 JAVA 移植版 TelephoneCheck.java (Ver 1.00 , 翻訳テーブル:2022/7/1 版) 】--------------------------- // // 電話番号のハイフン検証/編集関数 // ( ValidateTelephone / FormatTelephone / GetTypeTelephone / PhoneNumber ) // // 【 移植元ソース:番号翻訳テーブル 内包版 TelephoneCheck.js 】 // // Tips29: JavaScriptで電話番号(局番)のハイフン検証/編集 // http://addinbox.sakura.ne.jp/Excel_Tips29.htm // // Author : AddinBox(角田) http://addinbox.sakura.ne.jp/ // // β 1.00 , 2019/ 2/14 (JavaScript版 初版) // β 4.40 , 2019/ 3/27 (JavaScript版) // β 4.40 , 2019/ 3/27 (JAVA 移植版) // - - - - - - - - - - - - // Ver 1.00 , 2019/ 4/ 4 (JAVA 移植版, 番号翻訳テーブル:2019/4/1 版) // Ver 1.00 , 2019/ 5/11 (JAVA 移植版, 番号翻訳テーブル:2019/5/7 版) // Ver 1.00 , 2020/ 7/20 (JAVA 移植版, 番号翻訳テーブル:2020/6/1 版) // Ver 1.00 , 2022/ 8/ 2 (JAVA 移植版, 番号翻訳テーブル:2022/7/1 版) // // *1 固定電話番号は番号翻訳テーブルによって、全国の市外局番を忠実に判定します。 // 下記で翻訳テーブルの仕組みを確認できます。 // [ 電話番号翻訳テーブル 翻訳シュミレーター ] // http://addinbox.sakura.ne.jp/Excel_Tips29.htm#S2_2 //------------------------------------------------------------------------------- // 【 サポートしている電話番号 】 // 固定電話 10桁(先頭 0) [ 0ABCDE-FGHJ ] // 携帯電話 11桁(先頭 070/080/090) [ 0x0-CDEF-GHJK , C:1-9 ] 補:060は実施未定 // 着信課金 10桁(先頭 0120) [ 0120-DEF-GHJ ] // 着信課金 11桁(先頭 0800) [ 0800-DEF-GHJK ] // IP電話 11桁(先頭 050) [ 050-CDEF-GHJK , C:1-9 ] // M2M 11桁(先頭 020x) [ 020-CDE-FGHJK , C:1-3,5-9 ] // ポケベル 11桁(先頭 0204) [ 020-4DE-FGHJK ] // FMC 11桁(先頭 0600) [ 0600-DEF-GHJK ] // 情報料代理徴収 10桁(先頭 0990) [ 0990-DEF-GHJ ] ( 災害募金サービス ) // 全国統一番号 10桁(先頭 0570) [ 0570-DEF-GHJ ] ( NTT ナビダイヤル 等 ) //------------------------------------------------------------------------------- import java.util.regex.Pattern; public class TelephoneCheck { public TelephoneCheck() { } // 番号翻訳テーブル(2022/7/1 版) // 固定電話の全国の局番(市外局番+市内局番)および携帯電話(070/080/090)等の局番を // 収録しているJSONファイル(AreaCode4JSON.json)を必要最小限の内容に編集しています。 // 完全版のフォーマットは [ http://addinbox.sakura.ne.jp/Excel_Tips29.htm ] を参照の事。 // 尚、このJAVA用データはJSONファイル作成ツールで一緒に作成していますので、 // 「配列データ」の同一性/正確性は保障します。 // private static final int AreaCodeArray[][] = { {0,1,22,41,42,54,69,70,81,114}, {0,-3,2,4,7,10,15,19,20,21}, {-103,0,0,-4,-4,-4,3,0,0,0}, {0,0,-4,-4,-4,-4,-4,-5,0,0}, {0,0,0,-4,-4,-4,-4,5,-4,6}, {0,0,-5,0,-5,-4,-4,-5,-4,0}, {0,0,-5,-4,-4,-4,-4,-5,-5,0}, {0,0,-4,-4,-4,8,9,0,0,0}, {0,0,-4,-4,-4,0,-5,-5,0,0}, {0,0,-4,-4,-4,-4,-5,0,0,0}, {0,0,-4,-4,11,12,13,-4,14,0}, {0,0,-4,-4,-4,-4,-4,-5,-3,-4}, {0,-3,-4,-4,-4,-4,-4,-3,-5,-4}, {0,0,-4,-4,-5,0,-4,-4,0,0}, {0,0,-4,-4,-4,-4,-5,-5,-4,0}, {0,0,-4,16,17,18,-4,-4,0,0}, {0,0,-5,0,-5,-5,-4,0,-4,-4}, {0,0,-4,-4,-4,-4,-4,0,-5,0}, {0,0,-4,-4,-5,-5,-5,0,-5,0}, {0,0,-4,-4,-4,-4,-4,-3,-4,-4}, {0,0,-4,-4,-4,-4,-4,-4,-3,0}, {0,-4,-4,-4,-4,-4,-3,-4,-4,-3}, {130,0,23,25,26,27,32,34,36,39}, {-4,0,-3,24,-4,-4,-4,-3,-4,-4}, {-3,0,-4,-4,-3,-3,-3,-3,-3,-3}, {0,0,0,-4,-4,-4,-3,-4,-4,0}, {-4,-4,-4,-4,-4,-3,-4,-4,-4,-3}, {-4,0,-3,-3,-4,28,29,30,31,-4}, {-3,-3,-3,-3,-3,-3,-3,-4,-4,-3}, {-3,0,0,-4,-4,-4,-4,-4,-4,-4}, {-3,-3,-4,-4,-4,-3,-3,-3,-3,-3}, {-3,0,-4,-4,-4,-4,-4,-4,-4,-4}, {-4,-4,-3,-4,33,-4,-4,-4,-4,-4}, {-3,0,-4,-4,-4,-4,-3,-3,-3,0}, {-4,0,-3,-3,-4,0,-4,-4,35,-4}, {0,0,-4,-4,0,-4,-4,-4,-3,-3}, {-4,0,-4,37,-4,-4,-3,-4,-4,38}, {-3,0,-4,-3,-3,-4,-4,0,-4,-4}, {-3,0,0,0,0,-3,-4,-4,-4,-4}, {0,-4,-3,40,-4,-4,-4,-4,-3,-4}, {-3,0,-4,-4,-4,-3,-3,0,-3,0}, {0,0,0,-2,-2,-2,-2,0,0,0}, {0,0,43,47,-3,-3,48,49,51,52}, {-2,0,44,-3,-3,-3,-3,-3,45,46}, {-3,0,-4,-4,-4,-4,-4,-4,-4,-4}, {-3,-3,-4,-4,-3,-3,-3,-4,-4,0}, {-2,-3,-2,-2,-2,-2,-2,-3,-3,-2}, {0,0,-3,-3,-3,0,-4,0,-4,-4}, {-4,0,-3,-4,-3,-4,-4,-4,-3,0}, {50,-2,0,-3,-3,-4,-4,-3,-4,-4}, {-2,0,-4,-4,-4,-4,-4,-4,-4,-2}, {-4,0,-3,0,-3,-3,-3,-3,-3,-3}, {0,0,-3,-4,-4,-4,0,0,0,53}, {0,0,-5,0,-5,0,-5,0,-5,0}, {131,0,-3,55,59,60,61,62,64,65}, {0,-4,-4,-4,-3,-3,-4,-4,-4,56}, {0,0,-3,0,0,0,57,58,-3,0}, {0,-4,-4,-4,-3,-3,-3,-3,-3,-3}, {0,0,0,-3,-4,0,0,-4,0,0}, {0,0,-3,-3,-4,-4,-3,-4,-4,-3}, {-4,-4,-3,-4,-4,-4,-4,-4,-4,-3}, {0,-4,-4,-4,-4,-4,-4,-4,-4,-4}, {-110,0,-4,-4,-4,-4,63,-4,-4,0}, {0,0,-4,-4,-4,-4,-4,-4,0,-5}, {0,-4,-3,-3,-4,-4,-4,-4,0,0}, {0,0,-3,-3,-4,-4,-4,66,-4,68}, {0,0,-4,-4,-4,0,0,-4,-4,67}, {0,0,-5,-5,-5,-5,-5,-4,-4,-5}, {0,0,-4,-4,-4,-4,-4,-4,-4,-3}, {132,0,0,0,-2,0,-2,-2,0,0}, {133,0,71,72,73,-3,75,76,-3,77}, {0,-4,-3,-3,-3,-4,-3,-3,-3,-3}, {0,0,0,0,-3,-4,-4,-4,-4,-4}, {-4,0,-4,-4,-4,-4,74,-4,-4,-4}, {0,0,0,-4,-4,-4,-4,0,-5,0}, {0,-4,-3,-4,-3,-4,-4,-4,-4,0}, {-4,-4,-4,-4,-4,-3,-4,0,-4,-4}, {-4,-4,-3,-3,78,79,80,-4,-4,-4}, {0,0,-3,-3,-3,-3,-4,-4,-4,-3}, {-3,0,-4,-4,-4,-3,-3,-4,-4,-3}, {-3,0,-4,-4,-4,-4,-3,-3,-4,-4}, {134,0,82,87,94,96,98,111,112,113}, {-4,0,-3,-4,83,-3,-4,-4,-3,84}, {-3,0,-3,-3,-4,-4,-4,-4,-4,-3}, {-3,0,85,-4,86,-4,-3,-4,-4,0}, {-4,-3,-3,-3,-3,-3,-3,-3,-3,-3}, {-4,-3,-3,-3,-4,-4,0,0,0,0}, {0,0,-3,-4,-4,-4,88,89,91,92}, {-3,0,-4,-4,-4,-4,-4,-4,-4,-4}, {0,0,-4,-4,-4,-4,90,-3,-3,0}, {-4,0,-4,-4,-4,-4,-3,-3,-3,-4}, {0,0,-4,-4,-4,-4,0,-5,-5,0}, {-3,0,-3,-3,-3,-3,93,-3,-3,-3}, {0,0,-5,-3,0,-5,-3,-5,-5,0}, {0,0,0,0,0,-4,-4,95,-4,-3}, {0,0,-4,-4,-4,-4,-4,-5,-4,0}, {0,97,-4,-4,-4,-4,-4,-4,-4,-4}, {0,0,-5,0,-5,0,0,0,0,0}, {0,0,-3,99,-3,101,103,105,108,109}, {0,0,-4,-4,-4,-4,100,-4,-4,0}, {0,0,-3,-3,-3,0,-4,0,-3,0}, {0,0,-3,0,-4,102,-4,-4,0,0}, {-4,0,-3,0,-4,0,0,0,-4,0}, {-3,0,-4,-4,-4,-4,-4,-4,-4,104}, {-4,-3,-4,-4,-4,-4,-4,-3,-3,-4}, {0,0,106,107,-4,-4,-4,-4,-4,-4}, {0,0,-3,-3,-3,-4,-3,-4,-3,0}, {0,0,0,-4,-4,-4,-4,-3,-3,0}, {-3,0,-4,-4,-4,-4,-4,-4,-4,-3}, {-3,0,-4,-4,-3,-3,-4,-4,-4,110}, {0,0,-4,-4,0,-3,0,-3,0,-3}, {0,0,0,0,0,-4,0,-4,-3,-4}, {-4,0,0,-4,-4,-4,-3,-4,-3,-4}, {0,0,-4,-4,-4,-4,-4,-4,-4,-3}, {135,0,115,116,117,118,119,120,121,123}, {-4,0,-3,-3,-3,-3,-3,-3,-3,-3}, {-4,0,-3,-3,-3,-3,-3,-3,-3,-3}, {-4,0,-4,-4,-4,0,-4,-4,-4,-4}, {-4,0,-4,0,-4,-4,-4,-4,-3,-4}, {0,0,-3,-3,-4,-4,-4,-4,-4,-4}, {0,0,-4,-4,-4,-3,0,-4,-4,-4}, {122,0,-4,-4,-4,-4,-4,-4,-3,-3}, {0,0,-5,-4,-4,-4,-4,-4,-4,-4}, {-109,124,-3,125,128,-4,129,-4,-3,0}, {0,0,-5,-5,0,0,0,0,0,0}, {0,0,-4,126,127,-4,-4,-4,-4,0}, {0,-3,-4,-4,-4,-4,-4,-4,-4,-4}, {-4,-4,0,-3,0,-3,0,-3,0,-4}, {-3,0,-4,-4,-4,-4,-4,-3,-3,-4}, {0,0,-4,-4,-4,-4,-4,-4,-4,-5}, {0,-106,-106,-106,-107,-106,-106,-106,-106,-106}, {0,-105,-105,-105,-105,-105,-105,-105,-105,-105}, {-108,0,0,0,0,0,0,0,0,0}, {0,-102,-102,-102,-102,-102,-102,-102,-102,-102}, {-104,-102,-102,-102,-102,-102,-102,-102,-102,-102}, {0,-102,-102,-102,-102,-102,-102,-102,-102,-102} }; //------------------------------------------------------------------------------- // JavaScript版では返却値用の連想配列を初期化する InitTelephone 関数を用意しているが、 // JAVA版では返却値のスタイルをクラスオブジェクトにしている。 // 初期化はコンストラクタにて実施しているので、初期化関数 ( InitTelephone )は設けない。 //------------------------------------------------------------------------------- // 返却値のクラス定義( ValidateTelephone , FormatTelephone ) public static class TelephoneCheckValue { public int TelType; public int EditType; public String TelEdit; public int ErrId; public TelephoneCheckValue() { this.TelType = -1; this.EditType = 9; this.TelEdit = ""; this.ErrId = 0; } } // 返却値のクラス定義( GetTypeTelephone ) public static class TelephoneType { public int TelType; public int SizeAll; public int Size1; public int Size2; public int Size3; public int ErrId; public TelephoneType() { this.TelType = -1; this.SizeAll = 0; this.Size1 = 0; this.Size2 = 0; this.Size3 = 0; this.ErrId = 0; } } //------------------------------------------------------------------------------- // 電話番号のフォーマット&検証 ( PhoneNumber ) // --- ValidateTelephone/FormatTelephone の簡易インターフェース --- // // TelCode -- 半角文字列[ 0-9, -, (, ) ] // 固定電話/携帯電話などの[ハイフン/括弧]編集 or 未編集電話番号 // // Action -- "V" : 電話番号の検証 // "F1"〜"F6" : 電話番号の区切り編集( 2桁目が EditType の値 ) // // 返却値 // Action= "V" -- "0": 検証エラー , "1":検証OK , "2":検証OK(電話番号が数字のみ) // ( JAVA 版では 文字列の "0"/"1"/"2" が返ります) // // = "F1"〜"F6" -- 電話番号が正しい場合: EditType(2桁目)に従って編集した電話番号 // 電話番号が誤っている場合: "Phone Error" // // 上記以外 -- "" で返ります。 // //------------------------------------------------------------------------------- public static String PhoneNumber(String TelCode, String Action) { // FormatTelephone/ValidateTelephone の返却値 TelephoneCheckValue Result = new TelephoneCheckValue(); Pattern patternAction = Pattern.compile("^(([Ff][1-6])|[Vv])$"); // "F1"〜"F6" or "V" if (patternAction.matcher(Action).matches() != true) { return ""; } if ( (Action.toUpperCase()).equals("V") ) { Result = ValidateTelephone(TelCode); switch (Result.ErrId) { case 0: return "1"; // OK case 8: return "2"; // OK (電話番号が数字のみ) default: return "0"; // エラー } } else { Result = FormatTelephone(TelCode, Integer.parseInt(Action.substring(1)) ); if (Result.ErrId == 0) { return Result.TelEdit; } else { return "Phone Error"; } } } //------------------------------------------------------------------------------- // 電話番号の検証 ( ValidateTelephone ) // // TelCode -- 半角文字列[ 0-9, -, (, ) ] // 固定電話/携帯電話などの[ハイフン/括弧]編集 // // 返却値 -- class TelephoneCheckValue (TelType, EditType, TelEdit, ErrId ) // TelType 1:固定電話(10桁), 2:携帯電話(070/080/090,11桁), 3:着信課金(0120,10桁), // 4:着信課金(0800,11桁), 5:IP電話(050,11桁), 6:M2M(020x,11桁,x≠4), // 7:ポケベル(0204,11桁), 8:FMC(0600,11桁), 9:情報料徴収(0990,10桁), // 10:統一番号(0570,10桁), -1:other // // EditType 1: 0AB-CDE-FGHJ, 2: 0AB(CDE)FGHJ, 3: (0AB)CDE-FGHJ, 9:other // 携帯電話のみ、[3-4-4 桁]で区切る⇒1〜3 , [3-3-5 桁]で区切る⇒4〜6 // // TelEdit TelType/EditType で編集し直された電話番号(正しい編集結果) // ErrId=0/1/3/5 : 同じパターンで編集し直された電話番号 // 〃 =8 : ハイフン編集した電話番号 // 〃 =2 : TelCode のまま(未使用局番なので正誤は判断しない) // 〃 =4/6/9 : 空文字 // // ErrId 0:OK, 1:区切り位置不正, 2:未使用局番(固定電話), 3:市内局番1桁目が[0 or 1](固定電話), // 4:引数不正([数字,ハイフン,括弧]以外がある or 編集パターン不正 or '0'始まりでない or 桁数不足), // 5:引数不正(局番タイプに応じた桁数と不一致), // 6:その他のエラー, 8:OK(数字のみ指定), 9:引数未定義(TelCode) //------------------------------------------------------------------------------- public static TelephoneCheckValue ValidateTelephone(String TelCode) { // 返却値 TelephoneCheckValue Result = new TelephoneCheckValue(); // FormatTelephoneの返却値 TelephoneCheckValue ResultFormat = new TelephoneCheckValue(); // 携帯電話(3-3-5桁区切り編集の再取得用) TelephoneCheckValue ResultFormat2 = new TelephoneCheckValue(); String TelNumber; // ハイフン,括弧除去(数字のみ) int EditType; // 厳密なチェックは FormatTelephone の結果と比較して行なうので // 下記のパターンチェックでは桁数については曖昧で構わない('0'始まりのみチェックする) Pattern pattern0 = Pattern.compile("^0[0-9]+$"); // 0123456789 Pattern pattern1 = Pattern.compile("^0[0-9]+-[0-9]+-[0-9]+$"); // 012-345-6789 Pattern pattern2 = Pattern.compile("^0[0-9]+\\([0-9]+\\)[0-9]+$"); // 012(345)6789 Pattern pattern3 = Pattern.compile("^\\(0[0-9]+\\)[0-9]+-[0-9]+$"); // (012)345-6789 if (pattern0.matcher(TelCode).matches() == true) { // (数字のみ) 0123456789 // 数字のみ指定 ⇒ 編集のみ行って比較検証は無し ResultFormat = FormatTelephone(TelCode, 1); // ハイフン編集で固定 Result.TelType = ResultFormat.TelType; Result.EditType = 1; Result.TelEdit = ResultFormat.TelEdit; // ValidateTephone用エラーコードに差替え switch (ResultFormat.ErrId) { case 0: Result.ErrId = 8; // OK(数字のみ指定) break; case 1: Result.ErrId = 2; // 未使用局番(固定電話番号) break; case 2: Result.ErrId = 3; // 市内局番1桁目が[0 or 1](固定電話) break; case 3: Result.ErrId = 4; // 桁数不足(数字が10桁未満) break; case 4: Result.ErrId = 5; // 局番タイプに応じた桁数と不一致 break; default: Result.ErrId = 6; // その他のエラー } return Result; } else if (pattern1.matcher(TelCode).matches() == true) { // EditType:1 012-345-6789 EditType = 1; Result.EditType = 1; } else if (pattern2.matcher(TelCode).matches() == true) { // EditType:2 012(345)6789 EditType = 2; Result.EditType = 2; } else if (pattern3.matcher(TelCode).matches() == true) { // EditType:3 (012)345-6789 EditType = 3; Result.EditType = 3; } else { // [数字,ハイフン,括弧]以外がある or 編集パターン不正 or '0'始まりでない Result.ErrId = 4; Result.TelEdit = TelCode; return Result; } // FormatTelephone 用に[ハイフン,括弧]を除去して「数字のみ」にする TelNumber = TelCode.replaceAll("-|\\(|\\)",""); ResultFormat = FormatTelephone(TelNumber, EditType); // FormatTelephone で編集し直した結果と比較して検証する // ErrId で返るのは // 0:OK, 1:未使用局番(固定電話), 2:市内局番1桁目が[0 or 1](固定電話) // 3:引数不正(TelCode: 数字が10桁未満), // 4:引数不正(TelCode: 局番タイプの桁数と不一致) // 下記状態は既にチェック済なので、その値が返ることは無い // 3:引数不正(TelCode: ['0'始まりの数字]以外) // 6:引数不正(EditType) // 9:引数未定義(TelCode/EditType) Result.TelType = ResultFormat.TelType; Result.TelEdit = ResultFormat.TelEdit; // ValidateTephone用エラーコードに差替え switch (ResultFormat.ErrId) { case 0: // FormatTelephoneでOK ⇒ 正しい電話番号 if (TelCode.equals(ResultFormat.TelEdit)) { Result.ErrId = 0; // OK (区切り位置も正しい) } else { if (ResultFormat.TelType == 2) { // 携帯電話(070/080/090) // 携帯電話の場合、別の区切り方[3-3-5 桁]で再チェック ResultFormat2 = FormatTelephone(TelNumber, EditType + 3); if (TelCode.equals(ResultFormat2.TelEdit)) { // OK (3-3-5桁で一致) Result.ErrId = 0; Result.TelEdit = ResultFormat2.TelEdit; Result.EditType = EditType + 3; } else { Result.ErrId = 1; // 区切り位置不正 } } else { // 携帯電話 以外 Result.ErrId = 1; // 区切り位置不正 } } break; case 1: Result.ErrId = 2; // 未使用局番(固定電話番号) Result.TelEdit = TelCode; // ResultFormat.TelEdit(=TelNumber)なので入力値に差し替える break; case 2: Result.ErrId = 3; // 市内局番1桁目が[0 or 1](固定電話) break; case 3: Result.ErrId = 4; // 桁数不足(数字が10桁未満) break; case 4: Result.ErrId = 5; // 局番タイプに応じた桁数と不一致 break; default: Result.ErrId = 6; // その他のエラー } return Result; } //------------------------------------------------------------------------------- // 電話番号のハイフン編集 ( FormatTelephone ) // // TelCode -- 半角数字文字列[ 0-9 ], 10 or 11桁(先頭'0'固定) // 固定電話/携帯電話などの電話番号 // // EditType -- 数値 // 1or4: 0AB-CDE-FGHJ , 2or5: 0AB(CDE)FGHJ , 3or6: (0AB)CDE-FGHJ // 携帯電話のみ、[3-4-4 桁]で区切る⇒1〜3 , [3-3-5 桁]で区切る⇒4〜6 // // 返却値 -- class TelephoneCheckValue (TelType, EditType, TelEdit, ErrId ) // TelType 1:固定電話(10桁), 2:携帯電話(070/080/090,11桁), 3:着信課金(0120,10桁), // 4:着信課金(0800,11桁), 5:IP電話(050,11桁), 6:M2M(020x,11桁,x≠4), // 7:ポケベル(0204,11桁), 8:FMC(0600,11桁), 9:情報料徴収(0990,10桁), // 10:統一番号(0570,10桁), -1:other // // EditType 1or4: 0AB-CDE-FGHJ, 2or5: 0AB(CDE)FGHJ, 3or6: (0AB)CDE-FGHJ, 9:other // // TelEdit 編集された電話番号 // ErrId=0/2/4 : 編集された電話番号 // 〃 =1 : TelCode の内容のまま // 〃 =3/6/9 : 空文字 // // ErrId 0:OK, 1:未使用局番(固定電話), 2:市内局番1桁目が[0 or 1](固定電話), // 3:引数不正(TelCode: ['0'始まりの数字]以外 or 10桁未満), // 4:引数不正(TelCode: 局番タイプに応じた桁数と不一致) // 6:引数不正(EditType), 9:引数未定義(TelCode/EditType) //------------------------------------------------------------------------------- public static TelephoneCheckValue FormatTelephone(String TelCode, int EditType) { // 返却値 TelephoneCheckValue Result = new TelephoneCheckValue(); // GetTypeTelephone 返却値 TelephoneType ResultType = new TelephoneType(); Pattern TelPattern = Pattern.compile("^0[0-9]{9,}$"); // '0'始まりの数字文字列(10桁以上) // ['0'始まりの数字文字列(10桁以上)]のチェック // (番号翻訳(GetTypeTelephone)後に完全な桁数チェックを行なう。ここでは10桁未満のみNG) if (TelPattern.matcher(TelCode).matches() == false) { Result.ErrId = 3; return Result; } // EditTypeのチェック if (EditType >= 1 && EditType <= 6) { Result.EditType = EditType; // OK } else { Result.ErrId = 6; return Result; } ResultType = GetTypeTelephone(TelCode); // 番号翻訳して電話番号の種別と桁区切り情報を取得する // ErrId で返るのは // 0:OK, 1:未使用局番(固定電話), 2:市内局番1桁目が[0 or 1](固定電話) // 下記状態は既にチェック済なので、その値が返ることは無い // 3:電話番号種別が不明(桁数不足で番号翻訳未了)← 10桁以上なので未了は無い // 8:引数不正(TelCode: ['0'始まりの数字]以外) // 9:引数未定義(TelCode) Result.TelType = ResultType.TelType; Result.ErrId = ResultType.ErrId; if (ResultType.ErrId == 1) { // 未使用局番(固定電話) Result.TelEdit = TelCode; } else { // 0:OK or 2:市内局番1桁目が[0 or 1](固定電話) if (ResultType.TelType == 2 && EditType >= 4) { // 携帯電話(070/080/090)で[3-3-5 桁区切り, 0x0-CDE-FGHJK]を指定された場合 Result.TelEdit = InsertSeparator(TelCode, EditType, 3, 3); } else { // 携帯電話(3-4-4桁区切り)を含め、他は返却値で区切りパターンが得られる // 固定電話では[市外局番桁数/市内局番桁数/加入者番号桁数(4)]が得られる if (ResultType.Size2 == 0) { // 固定電話で、市内局番なし [ 0ABCDE-FGHJ ] (現在、この地域は存在しない) Result.TelEdit = TelCode.substring(0, 6) + "-" + TelCode.substring(6); } else { Result.TelEdit = InsertSeparator(TelCode, EditType, ResultType.Size1, ResultType.Size2); } } if (TelCode.length() != ResultType.SizeAll) { Result.ErrId = 4; // 桁数エラー(局番タイプに応じた桁数と不一致) } } return Result; } private static String InsertSeparator(String TelCode, int EditType, int Size1, int Size2) { String Result = ""; String EditCode1 = TelCode.substring(0, Size1); // 1st section :固定電話では市外局番(先頭'0') String EditCode2 = TelCode.substring(Size1, Size1 + Size2); // 2nd section :固定電話では市内局番 String EditCode3 = TelCode.substring(Size1 + Size2); // 3rd section :固定電話では加入者番号(末尾まで取り出す) switch (EditType) { case 1: // 0AB-CDE-FGHJ case 4: Result = EditCode1 + "-" + EditCode2 + "-" + EditCode3; break; case 2: // 0AB(CDE)FGHJ case 5: Result = EditCode1 + "(" + EditCode2 + ")" + EditCode3; break; case 3: // (0AB)CDE-FGHJ case 6: Result = "(" + EditCode1 + ")" + EditCode2 + "-" + EditCode3; } return Result; } //------------------------------------------------------------------------------- // 電話番号タイプの取得 ( GetTypeTelephone ) // // TelCode -- 半角数字文字列(2桁以上, 先頭'0'固定) // 固定電話/携帯電話などの電話番号(途中までの内容でも可) // // 返却値 -- class TelephoneType (TelType, SizeAll, Size1, Size2, Size3, ErrId) // TelType 1:固定電話(10桁), 2:携帯電話(070/080/090,11桁), 3:着信課金(0120,10桁), // 4:着信課金(0800,11桁), 5:IP電話(050,11桁), 6:M2M(020x,11桁,x≠4), // 7:ポケベル(0204,11桁), 8:FMC(0600,11桁), 9:情報料徴収(0990,10桁), // 10:統一番号(0570,10桁), -1:other // // SizeAll ErrId=0/2 : TelType に応じた電話番号の桁数(10 or 11, Size1〜3の合計値) // ErrId=1/3/8/9 : 0 // // Size1-3 ErrId=0/2 : TelType に応じた電話番号の区切り桁数(Size1 には先頭'0'含む) // ErrId=1/3/8/9 : 0 // (携帯電話(TelType=2)は[3-4-4 桁区切り]のみで返す) // // ErrId 0:OK, 1:未使用局番(固定電話), 2:市内局番1桁目が[0 or 1](固定電話), // 3:電話番号種別が不明(桁数不足で番号翻訳未了) // 8:引数不正(TelCode: ['0'始まりの数字]以外), 9:引数未定義(TelCode) //------------------------------------------------------------------------------- public static TelephoneType GetTypeTelephone(String TelCode) { // 返却値 TelephoneType Result = new TelephoneType(); int AreaCodeLength = 0; int CityCodeLength = 0; String CityCode1 = ""; // 市内局番の1桁目 int idx = 0; int cnt = 0; int num = 0; int LinkValue = 0; int TelType = 0; Pattern TelPattern = Pattern.compile("^0[0-9]+$"); // '0'始まりの数字文字列(桁数制限なし) // ( 1)固定電話 10桁 [ 桁区切りは番号翻訳結果に拠る ] // ( 2)携帯電話 11桁 [ 0x0-CDEF-GHJK , 070/080/090 ] // ( 3)着信課金 10桁 [ 0120-DEF-GHJ ] // ( 4)着信課金 11桁 [ 0800-DEF-GHJK ] // ( 5)IP電話 11桁 [ 050-CDEF-GHJK ] // ( 6)M2M 11桁 [ 020-CDE-FGHJK ] // ( 7)ポケベル 11桁 [ 020-4DE-FGHJK ] // ( 8)FMC 11桁 [ 0600-DEF-GHJK ] // ( 9)情報料代理徴収 10桁 [ 0990-DEF-GHJ ] // (10)全国統一番号 10桁 [ 0570-DEF-GHJ ] // SizeInfo [SizeAll, Size1, Size2, Size3] int SizeInfo[][] = { {0,0,0,0}, {10,0,0,0}, {11,3,4,4}, {10,4,3,3}, {11,4,3,4}, {11,3,4,4}, {11,3,3,5}, {11,3,3,5}, {11,4,3,4}, {10,4,3,3}, {10,4,3,3} }; // ['0'始まりの数字文字列(桁数制限なし)]のチェック if (TelPattern.matcher(TelCode).matches() == false) { Result.ErrId = 8; return Result; } // ※ 番号翻訳テーブルをソースコード内に直に収録しているので // JSONファイルの読み込み処理は必要ない。 // 番号翻訳テーブルから局番情報(市外局番の桁数 or [携帯番号 等]のTelType情報)を取得する。 // [TelCode]の長さが[局番桁数 未満]も受け入れているので『番号翻訳 途中』でのループ終了(TelType= -1)もある。 idx = 0; TelType = -1; AreaCodeLength = 0; for (cnt = 1; (cnt <= 5) && (cnt < TelCode.length()); cnt++) { // 番号翻訳テーブルはA〜Eコードの5段 num = Integer.parseInt(TelCode.substring(cnt, cnt + 1)); // 電話番号の2桁目以降(1桁目は'0')を順次取り出す LinkValue = AreaCodeArray[idx][num]; if (LinkValue == 0) { // 番号翻訳 終了(固定電話 未使用局番) TelType = 1; AreaCodeLength = 0; break; } else if (LinkValue < 0) { // 番号翻訳 終了 if (LinkValue > -100) { // 固定電話の市外局番桁数(符号反転値) 実際の収録値[ -2 〜 -5 ] TelType = 1; AreaCodeLength = LinkValue * (-1); // 市外局番 桁数決定(先頭の "0" 含む) } else { // 携帯電話 等のTelType値(符号反転値 - 100) 実際の収録値[ -102 〜 -110 ] TelType = (LinkValue * (-1)) - 100; } break; } else { // プラス値 idx = LinkValue; // 検索継続(収録値は NextIndex) } }; // TelType に応じた桁区切りを設定する // 固定電話(TelType=1)では市外局番桁数(AreaCodeLength)に従って設定する // Size1 の値は[先頭'0'含む] Result.TelType = TelType; switch (TelType) { case -1: // 電話番号種別が不明(桁数不足で番号翻訳未了) Result.ErrId = 3; break; case 1: // 固定電話 if (AreaCodeLength == 0) { // 未使用 局番 Result.ErrId = 1; } else if (AreaCodeLength == 6) { // 市内局番なし [ 0ABCDE-FGHJ ] (現在、この地域は存在しない) Result.ErrId = 0; Result.SizeAll = 10; Result.Size1 = 6; Result.Size2 = 0; Result.Size3 = 4; } else { CityCodeLength = 6 - AreaCodeLength; // 10 - AreaCodeLength - 4(加入者番号) if (TelCode.length() < (AreaCodeLength + 1)) { // [TelCode]が市内局番の桁位置までないので市内局番適否の判定不可⇒ OK で返す Result.ErrId = 0; } else { // FormatTelephone から呼ばれる場合は 10桁以上なので必ず判定可能 CityCode1 = TelCode.substring(AreaCodeLength, AreaCodeLength + 1); // 市内局番 1桁目 if (CityCode1 == "0" || CityCode1 == "1") { Result.ErrId = 2; // 市内局番1桁目に0/1は割り当てられない } else { Result.ErrId = 0; // OK } } Result.SizeAll = 10; Result.Size1 = AreaCodeLength; Result.Size2 = CityCodeLength; Result.Size3 = 4; } break; default: // TelType = 2〜10, SizeInfoテーブルから桁情報を設定する Result.ErrId = 0; // OK Result.SizeAll = SizeInfo[TelType][0]; Result.Size1 = SizeInfo[TelType][1]; Result.Size2 = SizeInfo[TelType][2]; Result.Size3 = SizeInfo[TelType][3]; } return Result; } }