文字列のバイト数をカウントする~mgrep.osax
「mgrep.osax」で文字列のバイト数をカウントしていましたが、
Snow Leopardになってから「mgrep.osax」が正しく動作しません。
「mgrep.osax」と同様のOSAXを他にご存知ないでしょうか。
iMac, Mac OS X (10.6.4)
「mgrep.osax」で文字列のバイト数をカウントしていましたが、
Snow Leopardになってから「mgrep.osax」が正しく動作しません。
「mgrep.osax」と同様のOSAXを他にご存知ないでしょうか。
iMac, Mac OS X (10.6.4)
レスがつかないので自己レスで……
いろんな板を巡って以下のようなスクリプトを見たのですが、
tell application "Finder"
set X to 0
set myname to name of (info for (choose file))
repeat with i in myname
try
if (ASCII character (ASCII number (contents of i))) = contents of i then
set X to X + 1
end if
on error
set X to X + 2
end try
end repeat
return X
end tell
これ単体では動作するのですが、これを長文スクリプトに組み込むと動作しないのだー、なぜか……
いろんな板を巡って以下のようなスクリプトを見たのですが、
tell application "Finder"
set X to 0
set myname to name of (info for (choose file))
repeat with i in myname
try
if (ASCII character (ASCII number (contents of i))) = contents of i then
set X to X + 1
end if
on error
set X to X + 2
end try
end repeat
return X
end tell
これ単体では動作するのですが、これを長文スクリプトに組み込むと動作しないのだー、なぜか……
ここがポイントになるはず.....なのですが・・・解決策を模索中。
お困りのようですね。AppleScript 2.0になってから、以前使えていたScripting Additionsが使えなくなって困ったものです。
上記のスクリプトですが、Finderのブロックにいれなくても、Standard Scripting Additionsだけだから、構わないように思うのですが、returnとの関係でしょうか。それから、Mac OS X 10.5あたりから、標準のファイル名は、UnicodeのUTF-8 Normalization Form D(http://unicode.org/reports/tr15/)で構成されています。ということで、日本語関係は、1文字につき3 Bytes、あるいは濁点や半濁点の場合は、それで1文字余分になりますので、6 Bytesの可能性があります。
Scripting Additionsを集めた、osaxen.comに、まだ使えるTextCommands.appというのがあります(http://osaxen.com/files/textcommands1.1.3.html)。これを使って書き直してみました。Xに文字列のサイズが入ります。また、countBytesを呼び出せば、文字列の長さをバイト単位で求めてくれます。一応、ASCIIの中に入らない(Unicodeでコードが256以上の文字)は、3 Bytesとカウントするようにしました。お試しください。
set myname to name of (info for (choose file))
tell application "TextCommands" to run
set X to my countBytes(myname)
on countBytes(s)
set X to 0
tell application "TextCommands" to set numList to unicode numbers s
repeat with i in numList
if i < 256 then
set X to X + 1
else
set X to X + 3
end if
end repeat
return X
end countBytes
rockdom さん
どのような処理を望まれているのかちょっと分からないので、2パターン書いておきます。サブルーチンBはちゃんとテストしてないのでちょっと心配...。
set myname to name of (info for (choose file)) as text
my get_bytes_len(myname)
-- サブルーチンA
-- UTF8のまま
-- 例「A」= 1バイト扱い、「あ」= 3バイト扱い、「ぷ」= 3バイト か 6バイト扱い
on get_bytes_len(str)
do shell script ("
printf '%s' " & quoted form of str & " |
perl -0ne 'print length $_;'
")
end get_bytes_len
-- サブルーチンB
-- ASCII等を1バイト、仮名漢字等を2バイトとして算出
-- 例「A」= 1バイト扱い、「あ」= 2バイト扱い
on get_bytes_len(str)
do shell script ("
printf '%s' " & quoted form of str & " |
perl -Mutf8 -MEncode -MUnicode::Normalize -MList::Util -CIO -0ne '
my @arr = ();
for my $i (split //, NFC $_) {
utf8::encode($i);
push (@arr, length $i > 2 ? 2 : 1);
}
print List::Util::sum @arr;
'
")
end get_bytes_len
これじゃだめですね。ボツにします。: Hiro.S
-------------------------
KyShin さん
重箱の隅をつつくようで申し訳ないんですが、重要なことなので一応。
> Mac OS X 10.5あたりから、
Mac OS X の最初のバージョンからです。
> 標準のファイル名は、UnicodeのUTF-8 Normalization Form D
正確には Mac OS X 独自仕様の NFD、いわゆる UTF8-MAC です。ご存知かもしれませんが、UTF8 NFD と UTF8-MAC を混同すると思わぬ文字化けの原因となります。ちなみに上のサブルーチンBのように NFC で正規化しても、テキスト処理だと特定の文字が化けます。本件では数を数えるだけなので問題はないのかなと。
Mac OS X 独自仕様の NFD
KyShinさん、Hiro.Sさん、ありがとうございます。
さっそく検証してみます。
職場のDTP環境はMac・Winが混在してるので
Macのみで作られた外部支給データはWindowsにコピーできないことがあります。
そのため31バイトを超えるロングネームファイルをピックアップする必要があるんです。
なるほど。でしたらスクリプト一括処理ではありませんが、Name Validator はどうでしょうか?バイト数以外にもいろいろできそうですよ。(使ったことないので使用感とかは分かりませんが...)
下記リンク先 > download からダウンロードできます。
ものかの
こんにちは。
ははぁ。
やっとわかってきました。
相手はWindowsのAFPサーバですね。(しかもちょい古目?)
WindowsのNTFSはUTF16の255文字までOKなので、31文字制限は旧MacのOS9との互換性のためのものです。
AFPサーバ部分が31文字で制限してるわけです。(AFP2.x?)
なので、OSXの上でUTF-8-MACでのByte数をカウントしてもダメですね。
MacRomanで31文字、漢字はShift-JIS(MacJapanese)で2byteコードというカウント。
ということになるのではないでしょうか。
ではでは。
文字列のバイト数をカウントする~mgrep.osax