SlideShare ist ein Scribd-Unternehmen logo
1 von 46
Downloaden Sie, um offline zu lesen
Perl I/O Layer
~ワイド文字のモダンな扱い方~


                      2011/06/13
      presented by : @yokomotod
内部表現にデコードしてから処理する

内部表現からエンコードして出力する

       以上。
             ね、簡単でしょう?
内部表現?
内部表現

= Perlが文字列を処理するときに
  内部で使っている表現

→ Perlは“文字”として認識できる
「Hello」という文字列は
データとしては
「0011010111011101010101・・・」
16進数だと
「0x48 0x65 0x6c 0x6c 0x6f」
アスキーコードの対応表で
’a’ = ‘0x48’ とか決まってるから、
「Hello」だと理解できる
ASCIIが世界のすべてだったら
これで終わり
しかし現実には

UTF-8
EUC-JP
SHIFT-JIS
LATIN-1
・・・
            ワイド文字ェ・・・
問
 「0x66 0x87 0x4e 0xba 0x30 0x81」
 を文字列に直せ
Perl「無理ッス。(文字コード何だよ・・・)」
Perl「仕方ないからそのままにしておこう」

$str =
‘0x66’, ‘0x87’, ‘0x4e’, ‘0xba’, ‘0x30’, ‘0x81’

 Not 内部表現
 バイナリ文字列、って呼ぶんだったような
$str =
 時間
‘0x66’, ‘0x87’, ‘0x4e’, ‘0xba’, ‘0x30’, ‘0x81’
       がな
              かっ
                    たの
print lenght($str); #=> 6
                          で未
print substr($str, 0, 3);    検証
                                !
#=> ‘0x66’, ‘0x87’, ‘0x43’  文字化け !
正規表現が複数バイト文字の一部分だけと
マッチしたり境界をまたいだり
文字コードを教えましょう
use Encode;

$decoded_str = decode(‘utf-8’, $str);




Perl「おk、utf-8な」
結局、内部表現って?



文字列を文字列として認識したPerlが、
内部でデータを保存しておく表現。
とはいえ、独自に特殊な保存形式を使っている
 とかではなく

ただ単にutf-8に変換して保持しているだけ

なので、内部表現に変換した文字列のことを
 utf8フラグがついている文字列、とも呼びます
た だ し
utf-8 の文字列を入力するなら変換しなくていい

ということではない。

utf8だろうがeuc-jpだろうが、
きちんと文字コードを伝えてあげないと、
Perlにとってはどちらも謎の数字列
さらに注意
内部表現は直接出力してはいけない。
wide character in print

というエラーに見覚えは?
内部表現は、あくまでPerl内部で扱う形式

端末がeuc-jp なら euc-jp を出してくれないと
文字化ける

そのまま出すのはオカシイ  だから警告
実は

内部表現はutf-8に過ぎないので、
端末がutf-8なら、そのまま出しても化けない

だ が し か し

きちんと変換するのが正しいマナー
例えばutf-8に変換するなら

use Encode;

print encode(‘utf-8’, $decoded_content);
ちなみに

Perlが理解できる形式に変換するから
decode

Perlがわからない形式に変換するから
encode
小休止。
どうやって内部表現に変換するか

(=どうやって文字コードを伝えるか)
基本中の基本

Encode.pm を使う

decode(‘utf-8’, $str);

encode(‘utf-8’, $decoded_str);
いちいち変換しないといけないのか?
                                           そんな仕様で大丈夫か?


open my $fh, ‘<‘, $filename or die $!;
while (<$fh>) {
  $line = decode(‘utf-8’, $_);
  chomp $line;
  my ($id, $title) = split /¥t/, $line;
  …
  print encode(‘utf-8’, $decoded_str). “¥n”;
}
close $fh;
大丈夫だ。問題ない。
open my $fh, ‘<:utf8’, $filename;

とすれば、読みだすデータに自動で
 decode(‘utf8’, $str)
binmode STDOUT, ‘:utf8’;

と書くと、
標準出力にprintするときに、自動的に
 encode(‘utf8’, $str)
binmode STDOUT, ‘:utf8’;

open my $fh, ‘<:utf8‘, $filename or die $!;
while (<$fh>) {
  chomp $line;
  my ($id, $title) = split /¥t/, $line;
  …
  print $decoded_str. “¥n”;
}
close $fh;
ソースコードに文字列を書くときも注意

if ($str =~ /牧田/ && $str =~ /かっこいい/) {
  # do something
}
else {
 die “error !”;
}
ソースコードの文字コードも、
Perlは知りません。
use utf8;

としてやると、ソースコードがutf8で
書かれていると認識されて、
ソース中の文字列が内部表現として認識される

当然、ソースコードはutf8で書くこと。
他には?
Perlへの入出力の整理

入力
 ファイル/ソースコード/MySQL/LWP

出力
 画面/ファイル/MySQL
ファイル
 open my $fh, ‘<:utf8’, $filename;
 open my $out, ‘>:utf8’, $filename;

画面
 binmode STDOUT, ‘:utf8’;

ソースコード
 use utf8;
MySQL
my $dbh = DBI->connect(
                       ‘dbi:mysql:database’,
                       ‘user’,
                       ‘passwd’,
                       {
                         mysql_enable_utf8 => 1,
                       }
                      ) or die $!;
データベース側のカラム設定がutf8文字に
なっていれば、自動で内部表現との変換を
やってくれる

(SELECTもINSERTも)

もしかしたら、binaryじゃなければいいかも?
僕は知りません。MySQLの文字コードをutf8
以外にしたことなんてないので。
LWP::UserAgent

my $res = LWP::UserAgent->get(…)
my $content = $res->decoded_content
まぁ忘れたら encode / decode で
ちなみに

utf-8 に encode / decode するときは

encode(‘utf8’, $str) としなくても

encode_utf8($str) というのがある

タイピングを2文字節約できるよ!
内部表現をマスターすれば
my $str = ‘今日はPerlのライトニングトーク。’;

length($str) #=> 19

substr(‘$str’, 0, 3) #=> ‘今日は’

$str =~ s/。/; #=> ‘‘今日はPerlのライトニングトーク’

split(//, $str)
 #=> (今 日 は P e r l のラ イ ト ニ ン ク ゙ ト ー ク 。)
Enjoy wide character !




See Also

Encodeでラクラク日本語処理 - JPerl Advent Calendar 2009
   http://perl-users.jp/articles/advent-calendar/2009/casual/10.html

Weitere ähnliche Inhalte

Was ist angesagt?

Lisp tutorial for Pythonista : Day 2
Lisp tutorial for Pythonista : Day 2Lisp tutorial for Pythonista : Day 2
Lisp tutorial for Pythonista : Day 2Ransui Iso
 
Lisp Tutorial for Pythonista : Day 3
Lisp Tutorial for Pythonista : Day 3Lisp Tutorial for Pythonista : Day 3
Lisp Tutorial for Pythonista : Day 3Ransui Iso
 
PHP AST 徹底解説
PHP AST 徹底解説PHP AST 徹底解説
PHP AST 徹底解説do_aki
 
Knct-SG #1 Parser入門
Knct-SG #1 Parser入門Knct-SG #1 Parser入門
Knct-SG #1 Parser入門y1r96 Ueno
 
謎の言語Forthが謎なので実装した
謎の言語Forthが謎なので実装した謎の言語Forthが謎なので実装した
謎の言語Forthが謎なので実装したt-sin
 
Php 12時間目(for文(ループ処理)応用)
Php 12時間目(for文(ループ処理)応用)Php 12時間目(for文(ループ処理)応用)
Php 12時間目(for文(ループ処理)応用)internous,inc.
 
エキ Py 読書会02 2章後半
エキ Py 読書会02 2章後半エキ Py 読書会02 2章後半
エキ Py 読書会02 2章後半Tetsuya Morimoto
 
プログラムの処方箋~健康なコードと病んだコード
プログラムの処方箋~健康なコードと病んだコードプログラムの処方箋~健康なコードと病んだコード
プログラムの処方箋~健康なコードと病んだコードShigenori Sagawa
 
F#入門 ~関数プログラミングとは何か~
F#入門 ~関数プログラミングとは何か~F#入門 ~関数プログラミングとは何か~
F#入門 ~関数プログラミングとは何か~Nobuhisa Koizumi
 
ちょっと詳しくJavaScript 第2回【関数と引数】
ちょっと詳しくJavaScript 第2回【関数と引数】ちょっと詳しくJavaScript 第2回【関数と引数】
ちょっと詳しくJavaScript 第2回【関数と引数】株式会社ランチェスター
 
【簡単テキストマイニング】歌詞から作品世界の魅力を探る
【簡単テキストマイニング】歌詞から作品世界の魅力を探る【簡単テキストマイニング】歌詞から作品世界の魅力を探る
【簡単テキストマイニング】歌詞から作品世界の魅力を探るShow T
 
2018年夏のPerl5
2018年夏のPerl52018年夏のPerl5
2018年夏のPerl5charsbar
 
Perl Parser Hacks vol.2
Perl Parser Hacks vol.2Perl Parser Hacks vol.2
Perl Parser Hacks vol.2Goro Fuji
 
Functional Pearl + Brainfuck
Functional Pearl + BrainfuckFunctional Pearl + Brainfuck
Functional Pearl + BrainfuckEita Sugimoto
 
スクリプトで文字コード変換
スクリプトで文字コード変換スクリプトで文字コード変換
スクリプトで文字コード変換1000 VICKY
 
from old java to java8 - KanJava Edition
from old java to java8 - KanJava Editionfrom old java to java8 - KanJava Edition
from old java to java8 - KanJava Edition心 谷本
 
Ruby講座第二回
Ruby講座第二回Ruby講座第二回
Ruby講座第二回mitsunaga
 

Was ist angesagt? (20)

Lisp tutorial for Pythonista : Day 2
Lisp tutorial for Pythonista : Day 2Lisp tutorial for Pythonista : Day 2
Lisp tutorial for Pythonista : Day 2
 
C-langage
C-langageC-langage
C-langage
 
Lisp Tutorial for Pythonista : Day 3
Lisp Tutorial for Pythonista : Day 3Lisp Tutorial for Pythonista : Day 3
Lisp Tutorial for Pythonista : Day 3
 
PHP AST 徹底解説
PHP AST 徹底解説PHP AST 徹底解説
PHP AST 徹底解説
 
Knct-SG #1 Parser入門
Knct-SG #1 Parser入門Knct-SG #1 Parser入門
Knct-SG #1 Parser入門
 
謎の言語Forthが謎なので実装した
謎の言語Forthが謎なので実装した謎の言語Forthが謎なので実装した
謎の言語Forthが謎なので実装した
 
Php 12時間目(for文(ループ処理)応用)
Php 12時間目(for文(ループ処理)応用)Php 12時間目(for文(ループ処理)応用)
Php 12時間目(for文(ループ処理)応用)
 
エキ Py 読書会02 2章後半
エキ Py 読書会02 2章後半エキ Py 読書会02 2章後半
エキ Py 読書会02 2章後半
 
プログラムの処方箋~健康なコードと病んだコード
プログラムの処方箋~健康なコードと病んだコードプログラムの処方箋~健康なコードと病んだコード
プログラムの処方箋~健康なコードと病んだコード
 
F#入門 ~関数プログラミングとは何か~
F#入門 ~関数プログラミングとは何か~F#入門 ~関数プログラミングとは何か~
F#入門 ~関数プログラミングとは何か~
 
Project coin
Project coinProject coin
Project coin
 
ちょっと詳しくJavaScript 第2回【関数と引数】
ちょっと詳しくJavaScript 第2回【関数と引数】ちょっと詳しくJavaScript 第2回【関数と引数】
ちょっと詳しくJavaScript 第2回【関数と引数】
 
【簡単テキストマイニング】歌詞から作品世界の魅力を探る
【簡単テキストマイニング】歌詞から作品世界の魅力を探る【簡単テキストマイニング】歌詞から作品世界の魅力を探る
【簡単テキストマイニング】歌詞から作品世界の魅力を探る
 
2018年夏のPerl5
2018年夏のPerl52018年夏のPerl5
2018年夏のPerl5
 
Python01
Python01Python01
Python01
 
Perl Parser Hacks vol.2
Perl Parser Hacks vol.2Perl Parser Hacks vol.2
Perl Parser Hacks vol.2
 
Functional Pearl + Brainfuck
Functional Pearl + BrainfuckFunctional Pearl + Brainfuck
Functional Pearl + Brainfuck
 
スクリプトで文字コード変換
スクリプトで文字コード変換スクリプトで文字コード変換
スクリプトで文字コード変換
 
from old java to java8 - KanJava Edition
from old java to java8 - KanJava Editionfrom old java to java8 - KanJava Edition
from old java to java8 - KanJava Edition
 
Ruby講座第二回
Ruby講座第二回Ruby講座第二回
Ruby講座第二回
 

Andere mochten auch

Google appsを便利に使って楽をしよう
Google appsを便利に使って楽をしようGoogle appsを便利に使って楽をしよう
Google appsを便利に使って楽をしようKenji Ono
 
情景画像文字認識に関連する研究者を募集します。
情景画像文字認識に関連する研究者を募集します。情景画像文字認識に関連する研究者を募集します。
情景画像文字認識に関連する研究者を募集します。陽平 山口
 
加賀さんと僕(実装編)〜艦これウィジェットの課題と実装〜
加賀さんと僕(実装編)〜艦これウィジェットの課題と実装〜加賀さんと僕(実装編)〜艦これウィジェットの課題と実装〜
加賀さんと僕(実装編)〜艦これウィジェットの課題と実装〜Hiromu Ochiai
 
タンゴチュウ in 名古屋ギークバー 2011.08.08
タンゴチュウ in 名古屋ギークバー 2011.08.08タンゴチュウ in 名古屋ギークバー 2011.08.08
タンゴチュウ in 名古屋ギークバー 2011.08.08陽平 山口
 
来栖川電算の技術紹介
来栖川電算の技術紹介来栖川電算の技術紹介
来栖川電算の技術紹介陽平 山口
 
加賀さんと僕 ~艦これウィジェットの紹介と説明~
加賀さんと僕 ~艦これウィジェットの紹介と説明~加賀さんと僕 ~艦これウィジェットの紹介と説明~
加賀さんと僕 ~艦これウィジェットの紹介と説明~Hiromu Ochiai
 
文字認識はCNNで終わるのか?
文字認識はCNNで終わるのか?文字認識はCNNで終わるのか?
文字認識はCNNで終わるのか?Seiichi Uchida
 
言語処理するのに Python でいいの? #PyDataTokyo
言語処理するのに Python でいいの? #PyDataTokyo言語処理するのに Python でいいの? #PyDataTokyo
言語処理するのに Python でいいの? #PyDataTokyoShuyo Nakatani
 
深層学習の非常に簡単な説明
深層学習の非常に簡単な説明深層学習の非常に簡単な説明
深層学習の非常に簡単な説明Seiichi Uchida
 
JAWS DAYS 2017 lunch session
JAWS DAYS 2017 lunch sessionJAWS DAYS 2017 lunch session
JAWS DAYS 2017 lunch session陽平 山口
 

Andere mochten auch (15)

Google appsを便利に使って楽をしよう
Google appsを便利に使って楽をしようGoogle appsを便利に使って楽をしよう
Google appsを便利に使って楽をしよう
 
PRML s1
PRML s1PRML s1
PRML s1
 
情景画像文字認識に関連する研究者を募集します。
情景画像文字認識に関連する研究者を募集します。情景画像文字認識に関連する研究者を募集します。
情景画像文字認識に関連する研究者を募集します。
 
Tesseract-OCR in iOS
Tesseract-OCR in iOSTesseract-OCR in iOS
Tesseract-OCR in iOS
 
加賀さんと僕(実装編)〜艦これウィジェットの課題と実装〜
加賀さんと僕(実装編)〜艦これウィジェットの課題と実装〜加賀さんと僕(実装編)〜艦これウィジェットの課題と実装〜
加賀さんと僕(実装編)〜艦これウィジェットの課題と実装〜
 
日中Ocr
日中Ocr日中Ocr
日中Ocr
 
タンゴチュウ in 名古屋ギークバー 2011.08.08
タンゴチュウ in 名古屋ギークバー 2011.08.08タンゴチュウ in 名古屋ギークバー 2011.08.08
タンゴチュウ in 名古屋ギークバー 2011.08.08
 
来栖川電算の技術紹介
来栖川電算の技術紹介来栖川電算の技術紹介
来栖川電算の技術紹介
 
OCRは古い技術
OCRは古い技術OCRは古い技術
OCRは古い技術
 
加賀さんと僕 ~艦これウィジェットの紹介と説明~
加賀さんと僕 ~艦これウィジェットの紹介と説明~加賀さんと僕 ~艦これウィジェットの紹介と説明~
加賀さんと僕 ~艦これウィジェットの紹介と説明~
 
文字認識はCNNで終わるのか?
文字認識はCNNで終わるのか?文字認識はCNNで終わるのか?
文字認識はCNNで終わるのか?
 
言語処理するのに Python でいいの? #PyDataTokyo
言語処理するのに Python でいいの? #PyDataTokyo言語処理するのに Python でいいの? #PyDataTokyo
言語処理するのに Python でいいの? #PyDataTokyo
 
Tesseract ocr
Tesseract ocrTesseract ocr
Tesseract ocr
 
深層学習の非常に簡単な説明
深層学習の非常に簡単な説明深層学習の非常に簡単な説明
深層学習の非常に簡単な説明
 
JAWS DAYS 2017 lunch session
JAWS DAYS 2017 lunch sessionJAWS DAYS 2017 lunch session
JAWS DAYS 2017 lunch session
 

Ähnlich wie Perl io layer

php7's ast
php7's astphp7's ast
php7's astdo_aki
 
私のSql -My Sql
私のSql -My Sql私のSql -My Sql
私のSql -My Sqlstiq 2e
 
Buffer overflow
Buffer overflowBuffer overflow
Buffer overflowionis111
 
Lisp batton - Common LISP
Lisp batton - Common LISPLisp batton - Common LISP
Lisp batton - Common LISPMasaomi CHIBA
 
Java8から17へ
Java8から17へJava8から17へ
Java8から17へonozaty
 
20080617 05 Mysql
20080617 05 Mysql20080617 05 Mysql
20080617 05 Mysqlstiq 2e
 
APASEC 2013 - ROP/JIT を使わずに DEP/ASLR を回避する手法を見てみた。
APASEC 2013 - ROP/JIT を使わずに DEP/ASLR を回避する手法を見てみた。APASEC 2013 - ROP/JIT を使わずに DEP/ASLR を回避する手法を見てみた。
APASEC 2013 - ROP/JIT を使わずに DEP/ASLR を回避する手法を見てみた。Satoshi Mimura
 
プログラミング言語 Ruby 2章 Rubyプログラムの構造と実行
プログラミング言語 Ruby 2章 Rubyプログラムの構造と実行プログラミング言語 Ruby 2章 Rubyプログラムの構造と実行
プログラミング言語 Ruby 2章 Rubyプログラムの構造と実行monglee
 
textsearch_jaで全文検索
textsearch_jaで全文検索textsearch_jaで全文検索
textsearch_jaで全文検索Akio Ishida
 
Lucene gosenの紹介 solr勉強会第7回
Lucene gosenの紹介 solr勉強会第7回Lucene gosenの紹介 solr勉強会第7回
Lucene gosenの紹介 solr勉強会第7回Jun Ohtani
 
Sagittariusの紹介
Sagittariusの紹介Sagittariusの紹介
Sagittariusの紹介Kato Takashi
 
初心者講習会資料(Osaka.R#7)
初心者講習会資料(Osaka.R#7)初心者講習会資料(Osaka.R#7)
初心者講習会資料(Osaka.R#7)Masahiro Hayashi
 
Material
MaterialMaterial
Material_TUNE_
 
知って得する標準関数の使い方
知って得する標準関数の使い方知って得する標準関数の使い方
知って得する標準関数の使い方Soudai Sone
 
Php in ruby
Php in rubyPhp in ruby
Php in rubydo_aki
 
Lisp tutorial for Pythonista : Day 1
Lisp tutorial for Pythonista : Day 1Lisp tutorial for Pythonista : Day 1
Lisp tutorial for Pythonista : Day 1Ransui Iso
 

Ähnlich wie Perl io layer (20)

PFI Seminar 2010/02/18
PFI Seminar 2010/02/18PFI Seminar 2010/02/18
PFI Seminar 2010/02/18
 
php7's ast
php7's astphp7's ast
php7's ast
 
私のSql -My Sql
私のSql -My Sql私のSql -My Sql
私のSql -My Sql
 
Buffer overflow
Buffer overflowBuffer overflow
Buffer overflow
 
Lisp batton - Common LISP
Lisp batton - Common LISPLisp batton - Common LISP
Lisp batton - Common LISP
 
Java8から17へ
Java8から17へJava8から17へ
Java8から17へ
 
20080617 05 Mysql
20080617 05 Mysql20080617 05 Mysql
20080617 05 Mysql
 
APASEC 2013 - ROP/JIT を使わずに DEP/ASLR を回避する手法を見てみた。
APASEC 2013 - ROP/JIT を使わずに DEP/ASLR を回避する手法を見てみた。APASEC 2013 - ROP/JIT を使わずに DEP/ASLR を回避する手法を見てみた。
APASEC 2013 - ROP/JIT を使わずに DEP/ASLR を回避する手法を見てみた。
 
プログラミング言語 Ruby 2章 Rubyプログラムの構造と実行
プログラミング言語 Ruby 2章 Rubyプログラムの構造と実行プログラミング言語 Ruby 2章 Rubyプログラムの構造と実行
プログラミング言語 Ruby 2章 Rubyプログラムの構造と実行
 
textsearch_jaで全文検索
textsearch_jaで全文検索textsearch_jaで全文検索
textsearch_jaで全文検索
 
What is Metasepi?
What is Metasepi?What is Metasepi?
What is Metasepi?
 
Lucene gosenの紹介 solr勉強会第7回
Lucene gosenの紹介 solr勉強会第7回Lucene gosenの紹介 solr勉強会第7回
Lucene gosenの紹介 solr勉強会第7回
 
Sagittariusの紹介
Sagittariusの紹介Sagittariusの紹介
Sagittariusの紹介
 
ATN No.2 Scala事始め
ATN No.2 Scala事始めATN No.2 Scala事始め
ATN No.2 Scala事始め
 
初心者講習会資料(Osaka.R#7)
初心者講習会資料(Osaka.R#7)初心者講習会資料(Osaka.R#7)
初心者講習会資料(Osaka.R#7)
 
Material
MaterialMaterial
Material
 
Introduction to Erlang/OTP
Introduction to Erlang/OTPIntroduction to Erlang/OTP
Introduction to Erlang/OTP
 
知って得する標準関数の使い方
知って得する標準関数の使い方知って得する標準関数の使い方
知って得する標準関数の使い方
 
Php in ruby
Php in rubyPhp in ruby
Php in ruby
 
Lisp tutorial for Pythonista : Day 1
Lisp tutorial for Pythonista : Day 1Lisp tutorial for Pythonista : Day 1
Lisp tutorial for Pythonista : Day 1
 

Perl io layer