@634

正規表現エディタ - 抽出条件のバリエーションを増やす

Advertisement

目標

  • 今までのURL抽出用コードに加え、メールアドレスや電話番号などを抽出できるようにする。
  • 抽出条件を自由に切り替えられるようにする。

フォーマットのクラス化

まず、抽象度を高めるためにインタフェースを定義する。

インタフェース:RegularExpression
package regularexpressioneditor.config;

public interface RegularExpression {
    // 論理名の取得
    public String getName();

    // 正規表現文字列の取得
    public String getRegularExpression();
}

いままでソースコードに直接記述していたURLを、上記のインタフェースを実装したクラスに変更する。
package regularexpressioneditor.config;

public class Url implements RegularExpression{
    // 論理名の取得
    public String getName() {
        return "URL";
    }

    // 正規表現文字列の取得
    public String getRegularExpression() {
        return "(http://|https://){1}[\\w\\.\\-/:]+";
    }
}

例として、電話番号を表すクラスも定義する
package regularexpressioneditor.config;

public class Tel implements RegularExpression{

    // 論理名の取得
    public String getName() {
        return "電話番号";
    }

    // 正規表現文字列の取得
    public String getRegularExpression() {
        return "\\d{3}-\\d{3}-\\d{4}|\\d{2}-\\d{4}-\\d{4}|\\d{4}-\\d{2}-\\d{4}";
    }
}

続いてこれらのクラスを管理するクラスを定義する。
RegularExpressionManagerクラス
package regularexpressioneditor.config;

import java.util.Vector;
import javax.naming.NamingException;

public class RegularExpressionManager {
    private Vector res = new Vector();

    // 初期化
    // 管理するクラスをインスタンス化する
    public RegularExpressionManager(){
        res.add(new Tel());
        res.add(new Url());
    }

    // 管理するクラス群を返す
    public Vector getWriters(){
        return res;
    }

    // 名前でクラスを検索する
    public RegularExpression lookup(String name) throws NamingException{
        for(int i = 0; i < res.size(); i++){
            RegularExpression re = (RegularExpression)res.elementAt(i);
            if(re.getName().equals(name)){
                return re;
            }
        }
        throw new NamingException(name + "はバインドされていません");
    }
}

既存コードへの組み込み

クラス化した正規表現群を、現行のコードに組み込む
MainFrameクラス
package regularexpressioneditor.gui;

import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.IOException;
import java.util.Vector;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.naming.NamingException;

import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JOptionPane;
import javax.swing.JRadioButtonMenuItem;
import javax.swing.ButtonGroup;
import javax.swing.JScrollPane;
import javax.swing.JSeparator;
import javax.swing.JTextPane;

import regularexpressioneditor.config.RegularExpression;
import regularexpressioneditor.config.RegularExpressionManager;

public class MainFrame extends JFrame{

    // 左パネル
    JTextPane text;                // テキストパネル
    JScrollPane spanel_left;    // スクロールパネル

    // 右パネル
    JTextPane result;            // テキストパネル
    JScrollPane spanel_right;    // スクロールパネル

    // メニュー
    JMenuBar menuBar;            //  メニューバー
    JMenu file;
    JMenu edit;
    JMenuItem open;
    JMenuItem save;
    JMenuItem quit;
    JMenuItem check;
    JMenu expression_choice;

    // 正規表現
    RegularExpressionManager expressionManager;
    RegularExpression expression;

    /**
     * 初期設定を行う
     */
    public MainFrame(){

        this.setDefaultCloseOperation(EXIT_ON_CLOSE);

        // 左ウィンドウ
        text = new JTextPane();
        spanel_left = new JScrollPane(text);

        // 右ウィンドウ
        result = new JTextPane();
        spanel_right = new JScrollPane(result);

        //メニュー
        menuBar = new JMenuBar();
        file = new JMenu("ファイル");
        edit = new JMenu("編集");
        open = new JMenuItem("開く");
        save = new JMenuItem("名前を付けて保存");
        quit = new JMenuItem("終了");
        check = new JMenuItem("文字列抽出");
        expression_choice = new JMenu("抽出対象");

        // 正規表現グループ
        expressionManager = new RegularExpressionManager();
        Vector expressionList = expressionManager.getWriters();
        ButtonGroup expressionGroup = new ButtonGroup();
        for(int i = 0; i < expressionList.size(); i++){
            String name = ((RegularExpression)expressionList.get(i)).getName();
            JMenuItem work = new JRadioButtonMenuItem(name);
            if(i == 0){
                work.setSelected(true);
                setExpressionSelectedItem(name);
            }
            expressionGroup.add(work);
            expression_choice.add(work);
            work.addActionListener(new ActionListener(){
                public void actionPerformed(ActionEvent e){
                    setExpressionSelectedItem(e.getActionCommand());
            }});
        }
        edit.add(expression_choice);

        // リスナ登録
        open.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent e){
                openDocument();
        }});
        save.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent e){
                saveDocument();
        }});
        quit.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent e){
                quit();
        }});
        check.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent e){
                check();
        }});

        //メニュー構築
        file.add(open);
        file.add(save);
        file.add(new JSeparator());
        file.add(quit);
        edit.add(check);

        //メニューバーにメニューを追加。
        menuBar.add(file);
        menuBar.add(edit);

        //メニューバーをコンテナに追加。
        setJMenuBar(menuBar);

        // スクロールバー設定
        spanel_left.setVerticalScrollBarPolicy(
            JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);
        spanel_right.setVerticalScrollBarPolicy(
            JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);

        // レイアウト
        this.getContentPane().setLayout(new GridLayout(1, 2));

        // パネル設定
        this.getContentPane().add(spanel_left);
        this.getContentPane().add(spanel_right);
    }

    //出力フォーマットの選択
    public void setExpressionSelectedItem(String name){
        try{
            expression = expressionManager.lookup(name);
        }catch(NamingException ne){
            ne.printStackTrace();
            System.exit(-1);
        }
    }

    //ファイルを開く
    public void openDocument(){
        try{
            text.setText(Dialog.open(this));
        }catch(IOException e){
            e.printStackTrace();
        }
    }

    //ファイルの保存
    public void saveDocument(){
        try{
            Dialog.save(this, result.getText());
        }catch(IOException e){
            e.printStackTrace();
        }
    }

    //プログラムの終了
    public void quit(){
        int result = JOptionPane.showConfirmDialog(
                     getContentPane(), "終了しますか?");
        if(result == 0){
            System.exit(0);
        }
    }

    //データ抽出
    public void check(){
        // URLを正規表現で定義
        Pattern pattern = Pattern.compile(expression.getRegularExpression());

        // 比較対照文字列
        Matcher matcher = pattern.matcher(text.getText());

        StringBuffer buffer = new StringBuffer();
        while(matcher.find()){                // 検索
            buffer.append(matcher.group());    // マッチした文字列取得
            buffer.append("\r\n");    // 改行
         }

        // テキスト設定
        result.setText(buffer.toString());
    }
}

動作イメージ

抽出条件選択
図1:抽出条件を選択する

URL抽出結果
図2:URLが抽出された。

電話番号抽出結果
図3:電話番号が抽出された。
警察総合相談電話番号 のデータを使用しました。

Advertisement

ショートカット

634
634ブログ
このカテゴリのトップページに戻る
Incubator(Pukiwiki)
634ラボ
   UIコレクションギャラリー
   ZO-3ジェネレーター

サイト検索


Y!ログール