Apple の脅威の通知と金銭目当てのスパイウェアへの対策について

しばらく返答が寄せられていないようです。 再度ディスカッションを開始するには、新たに質問してください。

Apple Scriptによる選択範囲の文字カウント(改行、スペース抜き)について

初めて質問させて頂きます。


文書作成でテキストエディットを使っているのですが、文字数のカウントができないため、以下の様なサイトを使用して文字数を都度調べている状態です。


http://www2u.biglobe.ne.jp/~yuichi/rest/strcount.html


上記のサイトは、改行を除いた文字数、改行、空白を除いた文字数を表示できるため、非常にありがたく使わせていただいていますが、Apple Scriptで同じことができないかと調べています。


以下のサイトにワードカウントの機能のApple Scriptがあるのですが、このscriptに改行、空白を除いた文字数カウントをするようにはどのようにできるのか、お教え願えればと思います。


http://macfan.jp/guide/2010/05/13/post_671.html


また、今回の件でApple Scriptを活用して色々と便利にMacを使いこなしたいので、上級者の方はどのような本などで勉強されてきたのかもお教え願えれば幸いです。

Mac mini, Mac OS X (10.7.5)

投稿日 2012/10/11 11:13

返信
スレッドに付いたマーク ベストな回答

投稿日 2012/10/12 07:17

こんにちは


ご指摘のJavascriptを用いた文字数カウンタと類似する機能のAppleScript例を下記に示します。

参考になれば幸いです。

--

on run

tell application "TextEdit"

set theText to the text of document 1

set word_count to count words of document 1

set char_count to count characters of document 1

set para_count to count paragraphs of document 1

end tell


set theLF to ASCII character 10

set LF_count to countSubstring(theText, theLF)

set space_count to countSubstring(theText, " ")

set show_words to "文字数:" & (char_count as string) & return & "改行を除いた文字数:" & ((char_count - LF_count) as string) & return & "空白、改行を除いた文字数:" & ((char_count - space_count - LF_count) as string) & return & "行数:" & (para_count as string)

set dialog_title to "TextEdit Word Count"

display dialog show_words with icon 1 with title dialog_title buttons {"OK"} default button "Ok"

end run


-- e.g. countSubstring("abc abc abc", "abc") --> 3


on countSubstring(theText, theSubstring)

-- ljr (http://applescript.bratis-lover.net/library/string/), modified from Aurelio.net (http://aurelio.net/doc/as4pp.html)

local ASTID, theText, theSubstring, i

set ASTID to AppleScript's text item delimiters

try

set AppleScript's text item delimiters to theSubstring

set i to (count theText's text items) - 1

set AppleScript's text item delimiters to ASTID

return i

on error eMsg number eNum

set AppleScript's text item delimiters to ASTID

error "Can't countSubstring: " & eMsg number eNum

end try

end countSubstring

--

参考文献:

http://applescript.bratis-lover.net/library/string/#countSubstring

http://hints.macworld.com/article.php?story=20070730101510623


動作環境:

-Mac OSX 10.6.8 Snow Leopard

-AppleScriptエディタ 2.3(118) / AppleScript 2.1.2

-テキストエディット 1.6(264)

返信: 45

2012/10/12 21:21 Hiro__S への返信

コメント、ありがとうございます。

Automatorの対策、大変参考になりました。

ご指摘の通り、課題はドキュメント全体でなく「選択したテキストの文字数」でした。

tell application "TextEdit"スコープ内のコードにつきまして、下記のように置き換えていただければ幸いです。

--

tell application "TextEdit"

set theText to the text of (the clipboard)

set word_count to count words of (the clipboard)

set char_count to count characters of (the clipboard)

set para_count to count paragraphs of (the clipboard)

end tell

--

2012/10/13 06:35 uni-factory への返信

uni-factory様


お世話になっております。


参考書籍のご提示ありがとうございます。


結構古い本のようですが、AppleScriptは昔からあるようですね。


じっくり時間をかけて、他にも色々とMacを操作できるようなので、勉強したいと思います。

2012/10/13 06:56 Hiro__S への返信

uni-factory様、Hiro.S様、HAL様


お世話になっております。


Perlというのは聞いたことはありますが、AutomatorではPerlもAppleScriptも使えるということでしょうか?


とても高度な質問になってしまったようで、皆様に恐縮です。


>>より多くのキャラクターにマッチします「全半角スペース+改行+タブ+そのた空白」


とある部分ですが、PerlとAppleScriptの場合、どちらが優れているとか、使いやすいとか、汎用性があるというのはあるのでしょうか?


kimukazu様にご回答頂いたスクリプトの結果は、非常に求めるものと近くなっており(ウィンドウで、文字数、空白抜きでの文字数が表示される点)ますが、Perlでもそれらのことは可能なのでしょうか?


また、kimukazu様のスクリプトでは、LFという表記が見受けられました。

(テキストファイルの改行コードの変換をWindowsへのファイル送信の際に行なっているのですが、その際は、変換ソフトを利用し、LF→CR+LFという形に変換しています。)


しかし、unifactory様の11:39の投稿にあるスクリプトには、改行コードについては記載がなく、Unicode textという記載がありますが、文字コードが決まると必然的に改行コードが決まるという事でしょうか?


多くの方々に細かくご検証、ご回答を頂き感謝しております。


ご返信の遅れならびに、当方の理解不足から、的確な質問ができていないかもしれませんが、ご回答いただければ幸いです。


2012/10/13 13:31 kimukazu への返信

kimukazu



お世話になっております。


ご丁寧なご回答並びに、複数のご提案ありがとうございます。


HTML+Javascriptでオフライン時に使えるようにするというのも考えましたが、調べ物を多くしながら文章を書くため、

できればサービスから文字カウントができればと考えています。


ご回答いただきましたスクリプトをAppleScriptエディタに貼り付けてみましたところ、

AppleScriptエラー(null)というものが出てきてしまいました。


その後、Automatorにて、サービス追加でAppleScriptを実行と操作し、スクリプトを保存してみました。


すると、選択した文字列をコピーもしくはカットした場合のみ、文字カウントが有効になりました。


(the clipboard)という部分がクリップボードにコピーされた文字列についてワードカウントを行うというスクリプトなのではないかと予想したのですが、この考えで正しいでしょうか?


しかし、文字の入力時にカウントをするため(誤ってコピーを二度してしまうなどすると、問題があるので)、できればクリップボードではなく、選択した範囲を文字カウントするように出来ればと思うのですが、技術的に可能でしょうか?


selected,highlightという文字列とword countで検索してみましたが、手がかりがつかめず、日本語での文字カウントは文字コードや改行コードなどの問題で難しいのかな?と思っています。


実際にAppleScript,Automatorで実行させていただいたスクリプトは以下になります。


<スクリプト>


on run {input, parameters}

tell application "TextEdit"

set theText to the text of (the clipboard)

set word_count to count words of (the clipboard)

set char_count to count characters of (the clipboard)

set para_count to count paragraphs of (the clipboard)

end tell


set theLF to ASCII character 10

set LF_count to countSubstring(theText, theLF)

set space_count to countSubstring(theText, " ")

set show_words to "文字数:" & (char_count as string) & return & "改行を除いた文字数:" & ((char_count - LF_count) as string) & return & "空白、改行を除いた文字数:" & ((char_count - space_count - LF_count) as string) & return & "行数:" & (para_count as string)

display dialog show_words with icon 1 buttons {"OK"} default button "Ok"

end run


-- e.g. countSubstring("abc abc abc", "abc") --> 3


on countSubstring(theText, theSubstring)

-- ljr (http://applescript.bratis-lover.net/library/string/), modified from Aurelio.net (http://aurelio.net/doc/as4pp.html)

local ASTID, theText, theSubstring, i

set ASTID to AppleScript's text item delimiters

try

set AppleScript's text item delimiters to theSubstring

set i to (count theText's text items) - 1

set AppleScript's text item delimiters to ASTID

return i

on error eMsg number eNum

set AppleScript's text item delimiters to ASTID

error "Can't countSubstring: " & eMsg number eNum

end try

end countSubstring


動作環境:

Mac OSX 10.7.5

テキストエディット バージョン1.7.1(289.5)

AppleScriptエディタ バージョン 2.4.3 (131.2)AppleScript 2.2.1

Automator バージョン 2.2.4 (339.2)


動作環境を記載しておらず、申し訳ありませんでした。


今朝方、投稿させていただいたと思っており、ご返信が遅くなり申し訳ございません。


ご回答いただければ幸いです。

2012/10/13 16:34 milestone への返信

Perlというのは聞いたことはありますが、AutomatorではPerlもAppleScriptも使えるということでしょうか?


はい。使えます。


PerlとAppleScriptの場合、どちらが優れているとか、使いやすいとか、汎用性があるというのはあるのでしょうか?


優劣:

AppleScript はアプリケーションとの情報のやり取りが得意ですが、テキスト処理や大量の情報処理は苦手です。一方 Perl はテキスト処理や大量の情報処理が得意中の得意ですが、アプリケーションとの情報のやり取りはできません。なので、どちらが優れているかということはではなく、両者の得意な部分を使うと良いと思います。


使いやすさ:

どちらが使いやすいとかはないと思います。ただ、「習得のしやすさ」は AppleScript の圧勝。Perl はとても難しいです。


汎用性:

AppleScript の中で Perl を使うこともできますし、Perl の中で AppleScript を使うこともできます。使いやすさは前者かなと思います。ほかの OS でもという意味では Perl。Windows でも Linux でも使えます。


kimukazu様にご回答頂いたスクリプトの結果は、非常に求めるものと近くなっており(ウィンドウで、文字数、空白抜きでの文字数が表示される点)ますが、Perlでもそれらのことは可能なのでしょうか?


可能です。また、unifactory さんのスクリプトでも可能です。


改行コード


unifactory さんのスクリプトにある「as Unicode text」は入力されたデータをテキストに変換する為の処理。kimukazu さんのものは「行数のカウント」の為の処理。どちらも「改行コード処理」ではありません。


-----


ところで、ちょっと確認ですが、milestone さんのご希望は「文字数」と「改行を除いた文字数」と「改行、空白を除いた文字数」の3項目ですか?また、「タブ」と「全角スペース」は「空白」として除外しても良いのでしょうか?

2012/10/13 23:36 milestone への返信

コメント、ありがとうございます。

AppleScriptで使用する場合は、最初の1行を下記のように修正({input,parameters}を削除)していただければエラーなしに動作可能と思います。

※Automatorでも今回のケースでは、{input,parameters}部分を削除しても影響はないと思います。

--

on run

--

(the clipboard)につきましては、ご指摘の通り、クリップボードの内容を示し、クリップボードにコピーした内容が文字カウント対象になります。

また、ご指摘の「選択した範囲」につきましてエディタ内のハイライト部分をお考えかと思いますが、その情報をクリップボードを用いずにそのまま他のプログラムに伝達するしくみにつきまして、Mac OSX内に存在するのかわかりません。

もし、ご存知でしたらお教えいただければ幸いです。(※Automatorのパラメータのinputを利用する方法があるのかも知れません。)

補足ですが、前稿記載のAppleScriptでは、コードの内容をご覧になればおわかりかと思いますが、改行をLFの数としてカウントし、空白は半角スペースのみをカウントしております。

空白に全角スペースを加えるには、

set spaceJ_count to countSubstring(theText, " ") --”全角スペース”数

としてカウントし、結果の表示の際に

"空白、改行を除いた文字数:" & ((char_count - space_count - spaceJ_count - LF_count) as string)

して減算すればよいかと思います。改行の定義の変更や、タブ等のカウントも同様ですので、ご希望に合うように修正していただき、正解のコードを共有していただければ幸いです。

2012/10/13 23:43 milestone への返信

uni-factory さんのスクリプトを発展させるとこんな感じになると思います。Mac OS X 10.6.8 で動作確認済み。Lion と Mountain Lion でも多分大丈夫。


なお、文字のフィルタリングには Perl を使用。「空白」は「改行・タブ・全半角スペース・そのた空白」で、計26文字。


-----


Automator サービス


受け取り:テキスト、検索対象:TextEdit

AppleScript を実行


on run {input}

try

set str to item 1 of input

set len to length of paragraphs of str

if last paragraph of str is "" then set len to len - 1

set s1 to "文字数     :" & (length of replace_str(str, ""))

set s2 to "改行を除外   :" & (length of replace_str(str, "\\n"))

set s3 to "改行と空白を除外:" & (length of replace_str(str, "\\s"))

set s4 to "行数      :" & len

set ss to s1 & return & s2 & return & s3 & return & s4 & return

tell application "TextEdit"

set btn1 to "OK"

set msg1 to "コマンド + C でコピーできます。"

set ttl1 to "文字数カウンター"

display dialog msg1 default answer ss buttons {btn1} default button {btn1} with title ttl1 with icon 1 giving up after 90

end tell

end try

end run

--

on replace_str(str, opt)

set sh1 to "printf '%s\\n' " & quoted form of str & " | "

set sh2 to "perl -CIO -pe 's|" & opt & "||g;'"

do shell script sh1 & sh2

end replace_str

2012/10/14 10:14 kimukazu への返信

kimukazu様


お世話になっております。


度々のご回答、ありがとうございます。


AppleScriptとAutomatorではスクリプトを変える必要があると知り、奥が深いのだなと感じております。


以下のようにスクリプトを変更し、Automatorで、


新規作成→サービス→AppleScriptを実行→"サービスは、次の選択項目を受け取ります:テキスト

→検索対象 : テキストエディット と選択し、以下スクリプトを貼り付け、実行いたしましたが、

構文エラー


"end"があるべきところですが unknown token が見つかりました と出てしまい、


サービスを保存し、テキストエディットでクリップボードにテキストをコピーし実行しても、


アクション "AppleScript" を実行でエラーが起きました と出てしまいます。


on run

tell application "TextEdit"

set theText to the text of (the clipboard)

set word_count to count words of (the clipboard)

set char_count to count characters of (the clipboard)

set para_count to count paragraphs of (the clipboard)

end tell


set theLF to ASCII character 10

set LF_count to countSubstring(theText, theLF)

set space_count to countSubstring(theText, " ")

set show_words to "文字数:" & (char_count as string) & return & "改行を除いた文字数:" & ((char_count - LF_count) as string) & return & "空白、改行を除いた文字数:" & ((char_count - space_count - spaceJ_count - LF_count) as string) & return & "行数:" & (para_count as string)

display dialog show_words with icon 1 buttons {"OK"} default button "Ok"

end run


-- e.g. countSubstring("abc abc abc", "abc") --> 3


on countSubstring(theText, theSubstring)

-- ljr (http://applescript.bratis-lover.net/library/string/), modified from Aurelio.net (http://aurelio.net/doc/as4pp.html)

local ASTID, theText, theSubstring, i

set ASTID to AppleScript's text item delimiters

try

set AppleScript's text item delimiters to theSubstring

set i to (count theText's text items) - 1

set AppleScript's text item delimiters to ASTID

return i

on error eMsg number eNum

set AppleScript's text item delimiters to ASTID

error "Can't countSubstring: " & eMsg number eNum

end try

end countSubstring


動作環境:

Mac OSX 10.7.5

テキストエディット バージョン1.7.1(289.5)

AppleScriptエディタ バージョン 2.4.3 (131.2)AppleScript 2.2.1

Automator バージョン 2.2.4 (339.2)

2012/10/14 10:17 Hiro__S への返信

Hiro.S様


お世話になっております。


ご回答ありがとうございます。


ご返信が遅くなりまして、申し訳ございません。


Perlのスクリプトは、非常に難しい印象を受けます。

(何を意味しているか理解できず、やはり難しいのだと認識しております。)


一方、AppleScriptはなんだか英語のような表記で読みやすいです。


当方の希望として、純粋に文字数だけの計測をしたいです。


よって、改行、空白、全角/半角スペース、タブを除いた文字数がわかればありがたいです。


Hiro.S様にご回答頂いたスクリプトで早速実行してみたところ、非常に使いやすく、問題無く動作しました。


このスクリプトはテキストエディットのみで作動するようですが、他のアプリケーションから実行する場合は、都度、スクリプトの以下の部分を変更し、Automatorでサービスとして保存する必要があるのでしょうか?


tell application "TextEdit"tell application "Safari" など


当方で最初、以下のように記述を変えてさせていただいたところ


tell application "TextEdit"

tell application "Safari"


としましたが実行できませんでした。


動作環境:

Mac OSX 10.7.5

テキストエディット バージョン1.7.1(289.5)

AppleScriptエディタ バージョン 2.4.3 (131.2)AppleScript 2.2.1

Automator バージョン 2.2.4 (339.2)

2012/10/14 13:23 milestone への返信

よって、改行、空白、全角/半角スペース、タブを除いた文字数がわかればありがたいです。


了解しました。


あと、「文字数」と「改行を除いた文字数」と「改行、空白を除いた文字数」の3項目を取得したいのか、「改行、空白を除いた文字数」のみを取得したいのか、あるいはそれ以外なのかもお聞きしたのですが...。これに関しては「上記3項目 + 行数」が見易いと思うので、そうさせていただきます。要するに、先のスクリプトのままにします。


このスクリプトはテキストエディットのみで作動するようですが、他のアプリケーションから実行する場合は、都度、スクリプトの以下の部分を変更し、Automatorでサービスとして保存する必要があるのでしょうか?


いいえ。スクリプトで吸収できます。Automator サービスの「検索対象」を「TextEdit」から「すべてのアプリケーション」に変更し、tell application "xxx" 部分をそれなりに書き換えます。ほかの箇所もちょっと書き換えたいので、再度アップします。少々お待ちを。

2012/10/14 13:33 milestone への返信

Automator サービス v2 です。「検索対象」を「すべてのアプリケーション」に変更するのをお忘れなく。


受け取り:テキスト、検索対象:すべてのアプリケーション

AppleScript を実行


on run {input}

try

set str to item 1 of input

set len to length of paragraphs of str

if last paragraph of str is "" then set len to len - 1

set s1 to "文字数     :" & length of new_str(str, "")

set s2 to "改行を除外   :" & length of new_str(str, "\\n")

set s3 to "改行と空白を除外:" & length of new_str(str, "\\s")

set s4 to "行数      :" & len

set ss to s1 & return & s2 & return & s3 & return & s4 & return

tell me to activate

using terms from application "Finder"

set btn1 to "OK"

set msg1 to "コマンド + C でコピーできます。"

set ttl1 to "文字数カウンター"

display dialog msg1 default answer ss buttons {btn1} default button {btn1} with title ttl1 with icon 1 giving up after 90

end using terms from

end try

end run

--

on new_str(str, opt)

set sh1 to "printf '%s\\n' " & quoted form of str & " | "

set sh2 to "perl -CIO -pe 's|" & opt & "||g;'"

do shell script sh1 & sh2

end new_str

2012/10/14 14:58 Hiro__S への返信

Hiro.S様


お世話になっております。


ご回答いただき有り難うございます。


しっかりとご質問にお答えしてらず申し訳ございません。


プログラムに触れることが殆どないため、不慣れな点があり、お手数をお掛けしております。


>あと、「文字数」と「改行を除いた文字数」と「改行、空白を除いた文字数」の3項目を取得したいのか、「改行、空白を除いた文字数」のみを取得したいのか、あるいはそれ以外なのかもお聞きしたのですが...。これに関しては「上記3項目 + 行数」が見易いと思うので、そうさせていただきます。要するに、先のスクリプトのままにします。


改行、空白を除いた文字数のみを取得したいです。


改行、空白、全角/半角スペースとタブそれぞれはカウントせず、文字だけの数を知りたいです。


当方の認識する文字数は、改行、空白、全角/半角スペースとタブを除外した文字数となります。


何文字以内という制約の文章を書くことが多いため、純粋に空白やスペース、タブ、改行がない文字だけの文字数が知りたいです。

(イメージとしては、印刷した時に目で見ることができる文字数で、PC上、スペースや半角が文字数としてカウントされるというようなことは考慮しないもものとしていただければと思います。)


以下は、Hiro.S様のご回答を頂いたことで、こういう機能が付加されたら便利かもしれないと考えた一案なのですが、ご回答いただければ(Perlによるスクリプトでの実行の可否や疑問点について)と思います。


・原稿用紙何枚というようなスタイルで文章を書く人にとっては、改行を除いた文字数がないと不便だと思いますし、原稿用紙換算で何枚かを換算する機能


一文が20文字以内もしくは、20文字で割ると余りが出る場合に1行とする処理が必要になるような気がしますが、そういう処理もPerlは得意な分野なのでしょうか?


・HTML形式でWebサイトのコンテンツを直打ちで既成のページのソースをベースに書き直すことなどもあるのですが、その際に、タグをカウント対象から外し、なおかつ実際にサイトを見るユーザーが見る文字数のみをカウントするという機能


この場合だと、除外するタグのリスト、メタタグやalt属性など文字がソース内に書かれているものの、実際には画面表示されない文字列の除外に関する処理が必要だと考えますが、とても複雑な処理かと思いますが、複雑な処理をさせることで処理に時間がかかって、スクリプトがアプリのようにクラッシュすることはあるのでしょうか?


動作環境:

Mac OSX 10.7.5

テキストエディット バージョン1.7.1(289.5)

AppleScriptエディタ バージョン 2.4.3 (131.2)AppleScript 2.2.1

Automator バージョン 2.2.4 (339.2)



2012/10/14 15:24 Hiro__S への返信

Hiro.S様


お世話になっております。


再三のご丁寧なご回答ありがとうございます。


Automatorにてサービスとして保存し、実行したところ、問題なく実行できました。


先ほどのtell application "TextEdit"と記載があった、2012/10/13 14:43Hiro.S様のご回答のスクリプトと、変更版のAutomator サービス v2では、ダイヤログボックスの画像がファイルのアイコンとテキストエディットのアイコンとで違いがあるようで、


tell me to activate

using terms from application "Finder"


の部分に違いがあるようですが、この部分はどのような効果があるのでしょうか?


Finderというと、ファイルがファイルが表示されたりするものという認識でしかないのですが…


また、OKボタンをマウスクリックではなく、returnキーで押せるようにして、できるだけマウス操作を減らし、ダイアログボックスが表示された状態でも他ウィンドウで文字入力の操作をしたり、ファイルやフォルダの作成をしたいので、そのように仕様の変更は可能でしょうか?


動作環境:

Mac OSX 10.7.5

テキストエディット バージョン1.7.1(289.5)

AppleScriptエディタ バージョン 2.4.3 (131.2)AppleScript 2.2.1

Automator バージョン 2.2.4 (339.2)

2012/10/14 15:49 Hiro__S への返信

Apple Support Communities

ご担当者様


以下のディスカッションにて、機能を知らず、すべての方に役に立つ回答ということでvoteさせていただこうとした際に、操作を誤ってしまいました。


自分の票をリセットすることは可能でしょうか?


ご回答よろしくお願いいたします。


milestone



2012年10月14日 13:54 Hiro.S <discussions@apple.co.jp>:


**

Apple Support Communities <https://discussions.apple.com> Re:

Apple Scriptによる選択範囲の文字カウント(改行、スペース抜き)について 作成者 Hiro.S<https://discussionsjapan.apple.com/people/Hiro.S?ac_cid=op123456>

Mac OS X Technologies フォーラム - クリックしてディスカッションの全文を表示<https://discussionsjapan.apple.com/message/100714169?ac_cid=op123456#100714169


Apple Scriptによる選択範囲の文字カウント(改行、スペース抜き)について

Apple サポートコミュニティへようこそ
Apple ユーザ同士でお使いの製品について助け合うフォーラムです。Apple ID を使ってご参加ください。