• ベストアンサー
  • すぐに回答を!

javascriptのmatchで質問です。

javascriptで入力された文字列の中から、指定した文字の前後の文字がアルファベッド、数字、ひらがな、空白かを判断するものを作成しています。 matchを使って作成を行っているのですが、なかなかうまくいっていないのが現状です。 どなたか知恵をお貸しいただけないでしょうか。 よろしくお願いします。 例 指定文字:1 入力:ABCD1EF 出力:アルファベッドです。 指定文字:う 入力:あいうえお 出力:ひらがなです。 指定文字:あ 入力:あいうえお 出力:前が空白で後ろがひらがなです。 という形にしたいです。

共感・応援の気持ちを伝えよう!

  • 回答数7
  • 閲覧数259
  • ありがとう数10

質問者が選んだベストアンサー

  • ベストアンサー
  • 回答No.5
  • think49
  • ベストアンサー率59% (285/482)

#2 です。汎用性を持たせるとして http://jsfiddle.net/JrxR3/ にコードを書いてみました。 ちなみに事例2は「文字列先頭」であって「空白」とは異なりますので先頭(begin)としました。 同じ理由で文字列末尾も end としています。 # このように区別しないと本当の空白「 」と区別が付かなくなります。 全角アルファベット、半角カタカナには対応していませんが、必要であれば function getCharType の内部コードを修正すれば対応できます。 文字コードはGoogle検索したり、 String#charCodeAt で調べてみてください。 # Re: 105atuさん

共感・感謝の気持ちを伝えよう!

質問者からのお礼

回答ありがとうございます! 詳しく書いていただき本当に助かりました。 参考になると同時に勉強になりました!

その他の回答 (6)

  • 回答No.7
  • think49
  • ベストアンサー率59% (285/482)

#2,5,6 です。#5 は古いバージョンのURLだったので下記URLに訂正します。失礼しました。 http://jsfiddle.net/JrxR3/4/

共感・感謝の気持ちを伝えよう!

  • 回答No.6
  • think49
  • ベストアンサー率59% (285/482)

#2,5 です。数字も対象に入っているようなので対応しました。 http://jsfiddle.net/JrxR3/2/ ■事例1 対象文字列: cccccc 検索文字列: c 結果: 前が begin で後が Alphabet です この事例では c は複数検出される可能性がありますが、初めに一箇所のみ検出する処理としています。 そうしないと単一の結果を返せないためです。 --- 余談。 私は正規表現を使用しない実装としましたが、正規表現で実装する場合はメタキャラクタに気をつける必要があります。 検索文字列を正規表現に組み込む処理において、検索文字列にメタキャラクタが含まれていたらエスケープさせないと検索文字列がメタキャラクタとして機能してしまいます。 --- #3 の方へ。 text.match, isFirst, isLast で3回検索しているようですが、この実装ではそれぞれマッチする場所が異なる場合があります。 対象文字列: cccccc 検索文字列: c 結果: 空白です。 初めの一回で全て検索しきってしまう実装が好ましいと思います。 > var re = text.match( (new RegExp("(.?)"+c+"(.?)")) ); . は改行を除くあらゆる文字にマッチしますので、前後に改行がある場合に期待通りに動作しません。 ^$ もまとめて検出するとして、下記のようにしてみてはどうでしょうか。 new RegExp('?:^|[\s\S])' + escapeRegExpString(c) + '(?:[\s\S]|$)') 空文字が格納された場合に ^$ と判定できます。 > function isAlpha(c){ 他の is**** シリーズにもいえることですが、この処理は部分一致のようですが、is を冠するなら完全一致であることを個人的に期待してしまいます。 この辺の実装は好みかもしれませんので強くは勧めませんが、参考までに。

共感・感謝の気持ちを伝えよう!

  • 回答No.4

思いつくまま書いてみました。未検証なのであしからず。 // TODO 文字が見つからない考慮が不足 文字の場所 = "入力された文字列".indexOf('指定した文字'); // TODO 文字の場所が文頭文末の考慮が不足 前の文字 = "入力された文字列".charAt( 文字の場所-1 ); 後の文字 = "入力された文字列".charAt( 文字の場所+1 ); function これは何ですか(文字){ _ _ if (/[A-Za-z]/.test(文字)) return 'アルファベット'; _ _ if (/[0-9]/.test(文字)) return '数字'; _ _ if (/[\u3040-\u309F]/.test(文字)) return 'ひらがな'; _ _ if (/\s/.test(文字)) return '空白'; _ _ return '何か'; } 前の種類 = これは何ですか(前の文字); 後の種類 = これは何ですか(後の文字); 出力 = 後の種類 + "です。"; if (前の種類 != 後の種類) { _ _ 出力 = "前が" + 前の種類 + "で後ろが" + 出力; }

共感・感謝の気持ちを伝えよう!

質問者からのお礼

回答ありがとうございます! 参考になります!

  • 回答No.3
  • taloo
  • ベストアンサー率44% (1016/2281)

自分に対しても文字種判定の練習になりそうだったので、考えてみました。 前後の1文字を取得して個別に判定するというパターンにしてますけど、これでいいのかどうか。。。 isAlpha(c) || isHiragana(c) || ・・・ という羅列がどうにも気に入らないのですが、これ以上思い浮かばないので。 各関数や判定結果を1つのオブジェクトにまとめて、ブラックボックスにした方がよさそうではあります。 <script> "use strict"; (function(window, document, undefined){ function $(id, val){ var el = document.getElementById(id); if( val!==undefined) { el.value=val; } return el.value; } var _judges=["", "空白", "アルファベット", "ひらがな"]; function isFirst(c, text){ return (new RegExp("^"+c)).test(text)? _judges.indexOf("空白"): 0; } function isLast(c, text){ return (new RegExp(c+"$")).test(text)? _judges.indexOf("空白"): 0; } function isAlpha(c){ return ( /[a-zA-Z]/.test(c) )? _judges.indexOf("アルファベット") : 0; } function isHiragana(c){ return ( /[あ-んを]/.test(c) )? _judges.indexOf("ひらがな") : 0; } function getCharType(c){ return isAlpha(c) || isHiragana(c) || 0; } function judge(){ var c = $('ipt_c'), text = $('ipt_text'), result = ''; var re = text.match( (new RegExp("(.?)"+c+"(.?)")) ); if( re ){ var before = isFirst(c, text) || getCharType(re[1]); var after = isLast(c, text) || getCharType(re[2]); if( before === after ){ result += _judges[ before ] + "です。"; }else{ result += "前が" + _judges[ before ] + "で後ろが" + _judges[ after ] + "です。"; } } $('ipt_out', result); } window.$ = $; window.judge = judge; })(this, document, void(0)); </script> HTMLを含めた全文はこちらで。 http://home.wi-wi.jp/lab/01d/

共感・感謝の気持ちを伝えよう!

質問者からのお礼

回答ありがとうございます! 全文載せていただき感謝です。 参考にさせていただきます!

  • 回答No.2
  • think49
  • ベストアンサー率59% (285/482)

アルファベットのケースのみ正規表現を書いてみました。 他の条件は応用してください。 <script> 'use strict'; function escapeRegExpChar (string) { return String(string).replace(/(?=[$()*+\-.?\[]^{|}])/g, '\\'); } function chkAlphabet (string, char) { if (String(char).length !== 1) return false; return new RegExp('[a-zA-Z]' + escapeRegExpChar(char) + '[a-zA-Z]').test(string); } console.log(chkAlphabet('ABCD1EF', 1)) // true console.log(chkAlphabet('AB12EF', 12)); // false </script> # Re: 105atuさん

共感・感謝の気持ちを伝えよう!

  • 回答No.1
  • yambejp
  • ベストアンサー率51% (3827/7415)

指定文字が入力文字の中に必ず1回(0回でも2回以上でもない)出現する という条件がつくのでしょうか? また前が数字で後がアルファベット的な表示もありうるということでよいですか? 加えてアルファベッド、数字、ひらがな、空白以外の文字が入力される可能性は想定しないのですか?

共感・感謝の気持ちを伝えよう!

質問者からの補足

返信が遅れてしまいすみません! 詳しく書かなくて申し訳なかったです。 指定文字が一回以上出現して、アルファベッド、数字、ひらがな、空白以外は基本的に想定してない です。 前が数字、後ろがアルファベッドの表示もありえる方向で考えてます。

関連するQ&A

  • javascriptで質問があります!

    こんにちは。 javascriptで、入力された文字列から指定された文字を含む行を抜き出すプログラムを作りたいです。 例: 入力された文字列 : abcd             efghi  指定した文字    :b 出力         :abcd こんな感じのプログラムを作りたいです。正規表現を使えばいけるのかなと思うのですがどなたか知恵をお貸しいただけないでしょうか? よろしくお願いいたします。

  • マルチバイト混在の文字列整形

    OS: Linux Ubuntu 言語: C++ 引数でchar*型の文字列配列(マルチバイト含む)を受け取り 指定した幅で枠つきで文字列を出力したいのですがうまくいきません。 作りたい出力 ━━━━━━━ ┃1: あいうえお┃ ┃2: かきく   ┃ ┃3: abc    ┃ ━━━━━━━ - str[] = {"あいうえお", "かきく", "abc"} - あいうえおの後ろは空白なし - 他は空白と文字列を合計してあいうえおと同じ長さに合うように 私の環境では日本語は3byteと認識され  strlen("あいうえお") = 15 となります。 イメージでは for (i = 0; i < strlen(str[])の最大値; i++) { cout << "┃" << i << ":" << setw(15) << left << str[i] << "┃" } のようなコードになると思うのですが 日本語一文字が出力上は2byte分の幅に見えるのに 認識としては3byteになってしまうので空白が1byte多くなり ━━━━━━━ ┃1: あいうえお┃ ┃2: かきく    ┃ ┃3: abc       ┃ ━━━━━━━ のようにずれてしまいます。 (表記上、最初の枠もずれていますが  現状は足りない分を埋めるsetfillが余計に働いてしまうということです。) 何か対策はありますでしょうか?

  • javascriptの配列の検索について

    テキストエリアに入力された文章を、改行ごとで配列に格納 その後、特定の文字を検索し、特定の文字がある配列を見つけて 見つかったものに処理をかけたいです 現在、配列に格納するところまでできているのですが、その後の文字を検索するところで躓いてます。 配列をmatchで検索すると一番最初の配列にのみ処理をかけてしまっているのが現状です。 どなたかお知恵を貸していただけないでしょうか よろしくお願いします。 例 入力された文字列:                明日の時刻のお知らせ                開始時間:10時30分                受付開始は10時00分からとなっております。                遅れないようにお願いいたします。 検索する文字:  時間     ↓ 検索ワードを含む配列:開始時間:10:30     ↓これに処理かけて 出力:10:30 検索ワードが見つからない場合 出力:10:00 10:30 という形にしたいです。 プログラムは下記のように組みました。 //////////////////////////// <html> <head> <script language="JavaScript"> function tester(){ var str= document.getElementById('input_text').value; var time; var alltime; abc = str.split(/\r\n|\r|\n/); var g = ["開始時間"]; for (var i=0;i<abc.length;i++){ if(abc[i].match(g)){ time = abc[i].match(/\d{1,2}:\d{1,2}/g); if(time2 !=null){ alert(time); document.write(time); break; } }else{ alltime = str.match(/\d{1,2}:\d{1,2}/g); if(alltime !=null){ document.write(alltime); } }break; } } </script> </head> <body> <textarea id=input_text rows="10" cols="45"> </textarea><br> <input type=button onclick="tester()" value="start"> </body> </html>

  • エクセルの質問をさせて下さい!

    今、帳票を作成するのに行き詰ってしまっています・・・。 画像を添付しますが、ABC(D)EF列とあって、 A列は数字/B列はアルファベット(大)/C列はひらがな/D列はなし/E列は 記号(もしくは漢字など)+アルファベット(大)+ひらがな+アルファベット(小)/F列は 空欄となっています。 E列にある文字の中で、B列にある「アルファベット(大)」&C列にある「ひらがな」が 合致しているものは、F列にA列の数字を返す、、、という事をしたいのです。 ※実際はB列の「アルファベット」・C列の「ひらがな」のそれぞれも1文字ではなく前後に  漢字等が入っていたりしますが、合致するキーワードで抽出出来れば。。。 分かりづらくて申し訳ありませんが、検索データが多く困ってしまっています。 (一つずつ照らし合わせていくのも時間がかかってしまって・・・) 宜しくお願いします!!!

  • 入力の文字が、アルファベットの小文字しかでなくなってしまいました。直し方を教えてください。

    多分、自分でどこかを押してしまったのだと思います。 入力の文字がアルファベットの小文字しかでません。ただ、それはインターネットのURLが表示されている場合だけのようで、メモ帳やチャットのメッセンジャー等では,普通に打ちこめます。 そして、ツールバーやF6キーでひらがなにして検索の枠などに打ち込もうとすると、カーソルが勝手にURLの欄に飛んでしまい、アルファベッドの小文字に。もどしてもひらがなになおすとまた、とんでしまいます。 今は、ここに打ち込むこともできず、メモ帳を開き、そこに入力したものをコピーしてここにはりつけています。

  • c#で正規表現を使用してのmatchがうまくいきません。

    c#で正規表現を使用してのmatchがうまくいきません。 例えば以下のようなタグがあったとします この6行をmatchの対象の文字列としたとします。(タグは適当です) ---------------------------------------- <select class="iiy_name_list"> <option value="1347">abc</option> </select></td> <select class="sug_name_list"> <option value="761">def</option> </select></td> ---------------------------------------- 2行目の"abc"を含む列が欲しかったので、以下のように正規表現にてキャプチャ範囲を指定 @"<option\s+value=""1347"">(.*)</select></td>", しかし、”(.*)”以降に指定した"</select></td>"というタグは match対象の全体分には2箇所全く同じ物があるため、2回目に出現した"</select></td>"まで読み込み、不必要なdefの行までも取得してしまいます。 "</select></td>"以外に正規表現で指定できる文字はありません、 ”(.*)”以降に指定した"</select></td>"が最初に出現した場所までをキャプチャし、2回目に出現してもキャプチャの範囲対象外にするには どのようにすればよいのでしょうか? よろしくお願いします。

  • preg_matchでの コンマ について 

    phpでの正規表現で 「もしも変数$wordへ入力した文字列が Japan's という文字列に一致すれば」というスクリプトを作成しましたが、うまくいきません。 if(preg_match("/japan\'s/i",$word,$match)){ この Japan's における カンマの取り扱いを このケースではどうしたらいいかよくわかりません。 \' としてみましたが、うまくいきません。 なにかアドバイスやヒントがありましたら、よろしくお願いします。 ああでもない、こうでもないとやってみましたが、その過程で 唯一 Japan's にヒットしたのは、次のスクリプトでした。 if($word=="japan\'s") ただし、これは正規表現は使っていないわけですよね。 なにか、自分のローカル環境に問題があるのかと思い、レンタルサーバーに同じものをuploadして試して見ましたが、やはり結果は同じで、ヒットしませんでした。別のパソコンでもやってみましたが、結果は同じでした。 整理しますと、 (preg_match("/japan's/i",$word,$match) ではヒットせず、よって コンマの前に\をつけて(preg_match("/japan\'s/i",$word,$match) としましたが、これもヒットしなかったということになります。 1) (')は正規表現の特殊文字でないはずですから、そのまま使えるはずだと思いましたが、なぜかこれが使えない。 2) しかも、その前にエスケープの \ をつけても、そのエスケープ が効かないのはなぜか。 追記: 最近分かったこと。 おもしろいことに、 'j すると、hitする。でも、j' とするとヒットしない。 ということは、コンマ自体には問題ないのだろうと推測しています。でも、文字の後にコンマがつくと、preg_matchにとって特別な意味を持つ文字列に変わるのではないか。

    • ベストアンサー
    • PHP
  • エクセル マクロ 出力と移動

    Private Sub CommandButton1_Click() Range("B8").Value = 1856 Range("B9").Value = "abc" Range("B11:D13").Value = "abc" End Sub (1)シート1にボタンを作成して出力できるようにしたのですがシート2に出力したい (2)(1)の続きでボタンを押した時、文字が入力後にそのシートに飛ぶようにしたいのですが どうすればいいでしょうか?

  • excelの質問

    以下のことをやりたいのですが、 セルに入れる式を教えて頂けないでしょうか。 ------------------------------------------------- (1)指定セルが空白でない YES⇒指定セルの文字を出力 NO⇒(2)へ (2)1マス左のセルが空白でない YES⇒「その列の2行目のセルの文字」+「そのセルの文字」を出力 NO⇒(2)を繰り返す。 ------------------------------------------------- (2)は5回くらい繰り返せばOKな状況です。 お手数ですがお願いしますm(_ _)m

  • EXCElの数式教えて下さい

    例えば、A1が空白の場合D1わ空白、Alが文字など入力済みの場合わD1に手入力で好みの文字を入力出来る数式を教えて下さい。 宜しくお願いいたします。