質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.49%
PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

CakePHP

CakePHPは、PHPで書かれたWebアプリケーション開発用のフレームワークです。 Ruby on Railsの考え方を多く取り入れており、Railsの高速性とPHPの機動性を兼ね備えています。 MVCやORMなどを「規約優先の考え方」で利用するため、コードを書く手間を省くことができます。 外部のライブラリに依存しないので、単体での利用が可能です。

正規表現

正規表現とは特定の文字列によるパターンマッチングを行う際に用いられる宣言型プログラミングです。

Q&A

解決済

3回答

1354閲覧

PHPで文字列にSJIS有効範囲外の文字が入っていないかのチェック方法

nata-de-Gollira

総合スコア42

PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

CakePHP

CakePHPは、PHPで書かれたWebアプリケーション開発用のフレームワークです。 Ruby on Railsの考え方を多く取り入れており、Railsの高速性とPHPの機動性を兼ね備えています。 MVCやORMなどを「規約優先の考え方」で利用するため、コードを書く手間を省くことができます。 外部のライブラリに依存しないので、単体での利用が可能です。

正規表現

正規表現とは特定の文字列によるパターンマッチングを行う際に用いられる宣言型プログラミングです。

0グッド

1クリップ

投稿2022/08/26 09:37

前提

  • PHP 7.1
  • cakePHP3
  • 文字コード:UTF8

実現したいこと

入力文字にSJISの有効範囲外の文字が使用されていないかをチェックしようとしています。
システム自体はUTF8なのですが、入力値をSJISのCSVに出力するため入力時にバリデーションをかけようとしていますが上手く検知できません。

発生している問題・エラーメッセージ

入力値を正規表現を使ってバリデーションしたいと考えております。
mb_ereg を使えばチェック可能かと思っていたのですが上手く判定してくれません。

該当のソースコード

// sjis範囲外文字 $check = '﨑' $pattern = "[^" . "(\x{0a})|" . "(\x{20}-\x{7E})|" . "(\x{8140}-\x{819E})|" . "(\x{819F}-\x{81AC})|" . "(\x{81B8}-\x{81BF})|" . "(\x{81C8}-\x{81CE})|" . "(\x{81DA}-\x{81E8})|" . "(\x{81F0}-\x{81F7})|" . "(\x{81FC})|" . "(\x{839F}-\x{83B6})|" . "(\x{83BF}-\x{83D6})|" . "(\x{8440}-\x{8460})|" . "(\x{8470}-\x{8491})|" . "(\x{849F}-\x{84BE})|" . "(\x{824F}-\x{8258})|" . "(\x{8260}-\x{8279})|" . "(\x{8281}-\x{829A})|" . "(\x{829F}-\x{82F1})|" . "(\x{8340}-\x{8396})|" . "(\x{889F}-\x{989E})|" . "(\x{989F}-\x{9FFC})|" . "(\x{E040}-\x{EAA4})" . "]" ; $enc_str = mb_convert_encoding($check, 'sjis-win'); mb_regex_encoding('sjis-win'); if (mb_ereg($pattern, $enc_str)) { // ここに入って欲しいが入ってくれない }

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答3

0

ベストアンサー

Shift_JISに変換した結果をさらUTF-8に変換して、元の文字列と一致しているかで確認する方法はどうでしょうか?

投稿2022/08/26 11:18

ockeghem

総合スコア11701

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

nata-de-Gollira

2022/08/29 08:28

すんごい、正規表現を使う事に囚われており目からウロコでした! シンプルイズベストな回答ありがとうございました。
guest

0

Rubyだとエンコーディング変換の時に変換できない文字があったらその文字を引数にコールバックのメソッドを呼び出せるのですが、他の言語だとそこまで細かい対応はできないですね。

質問文でSJISと書きつつコードに書いてあるのはsjis-winですが、どちらの範囲が対象なのでしょう?
を駄目としたいようなので、とりあえずSJISの範囲として書きます(JIS-X0208の範囲)。

mb_convert_encoding($check,"sjis")で、SJISに無い文字は?に変換されるようなので、
変換後の文字列に?があったら元の文字列の該当位置を調べて?でなかったらSJISにない文字だと判断できそうな気がします。

どの文字がおかしいまで知る必要ながなくて、全体としてOKかNGかだけであれば、?の個数を比較すればいいかと。

投稿2022/08/26 11:10

編集2022/08/26 11:22
otn

総合スコア84491

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

otn

2022/08/26 11:26

あ、全体としてOKかNGであれば、ockeghemさんの回答が明快ですね。 よくやる方法なのに、どの文字かを調べる頭になってたので、出てきませんでした。
otn

2022/08/26 11:48 編集

なお、正規表現部分は、$pattern = "/[^" . "\x0a" . "\x20-\x7E" . "\x81\x40-\x81\x9E" ~~中略~~ "]/"; のように書くのが正しいと思いますが、PHPだとUTF-8でないと範囲( [あ-お] とか)は駄目なようです。 SJISにすると mb_ereg("い", "/[あ-お]/") が偽になる。
nata-de-Gollira

2022/08/29 08:29

回答ありがとうございました! 正規表現の書き方情報も助かりました!今後に役立てます!
guest

0

SJISではなくSJIS-WINに変換すればよいのでは?
HTTPヘッダも

PHP

1header('Content-Type: text/html;charset=Windows-31J');

としてください

投稿2022/08/26 09:50

yambejp

総合スコア114747

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

yambejp

2022/08/29 08:51 編集

ん・・・タツサキやハシゴダカあたりはsjis-winとheader設定でいけるんですけどね・・・ header('Content-Type: text/html;charset=Windows-31J'); $check="崎﨑高髙"; // utf8 $enc_str = mb_convert_encoding($check, 'sjis-win'); print $enc_str; ※utf8はBOMなしで保存すること
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.49%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問