英語短縮表記への半角スペース追加No.10037
楽になりたい さん 22/12/29 22:42
 
ラジオでオンエアされた楽曲の成型マクロを作ろうとしています。

演奏者やタイトルに、Dr. Mrs. などの略語が含まれる場合、日本人の作成したプレ
イリストではピリオドの直後に半角スペースが続いたり続かなかったりします。
外国サイトなどを検索してみると、どうやらピリオドの直後に半角スペースが続くの
が正しいようです。

そこで次のようなマクロでとりあえず追加できるようになりました。

replacedown "([(Mstr)|(Sir)|(Mr)|(Mrs)|(Ms)|(Dr)|(Prof)|(Esq)|(Mx)]\\.)", "\
\1 ", regular, nocasesense, nohilight ;

ところが、希望していない場所にも半角スペースが追加されてしまう事に気が付きま
した。
例えばこのプレイリスト。

O.I.L. (CAN'T GET ENOUGH OF THAT STICKY) / JEFF BECK
ENGLAND LOST / MICK JAGGER feat. SKEPTA
LET IT DIE / OZZY OSBOURNE
LUCKY ONE ft. K. FLAY / TOM MORELLO
O.I.C. / ELECTRIC MARY
PERMANENT VACATION / AEROSMITH

最初の行のO.I.L.にも追加されてしまいます。下から2行目のO.I.C.にも追加されて
しまいます。

試行錯誤を続けていますが、どうしても直すことができません。
マクロというよりは、正規表現よりの内容ですが、よろしくお願いします。

[ ]
RE:10037 英語短縮表記への半角スペース追No.10038
でるもんたいいじま さん 22/12/29 23:15
 
こんにちは、秀丸愛用者の「でるもんた・いいじま」です。

> 演奏者やタイトルに、Dr. Mrs. などの略語が含まれる場合、
....
> ピリオドの直後に半角スペースが続くのが正しいようです。
>
> そこで次のようなマクロでとりあえず追加できるようになりました。
> replacedown "([(Mstr)|(Sir)|(Mr)|(Mrs)|(Ms)|(Dr)|(Prof)|(Esq)|(Mx)]\\.)",
>"\\1 ", regular, nocasesense, nohilight ;
> ところが、希望していない場所にも半角スペースが追加されてしまう事に気が付き
>ました。

replacedownに与える正規表現が正しくありません。
特に、[...] の使い方が違います。
[...] はたとえば "M[rsx]" のように使います。
この例だと、「Mのあとにr,s,xのいずれかが続くもの」という意味になります。
[...] の中に指定できるのは1文字単位の文字(あるいは a-z のような範囲指定)だ
けで、
2文字以上の塊は残念ながら [...] の中には指定できません。

今回はおそらく、
replacedown "(Mstr|Sir|Mr|Mrs|Ms|Dr|Prof|Esq|Mx)\\.)", "\\1 ", regular, noca
sesense, nohilight ;
で行けるはずです。

あとは個人的には、最初からピリオドのあとにスペースが入っている場合に余計なス
ペースを付け足さないように、
replacedown "(Mstr|Sir|Mr|Mrs|Ms|Dr|Prof|Esq|Mx)\\.)\s*", "\\1 ", regular, n
ocasesense, nohilight ;
と手直ししたくなりますが、この修正を入れるかどうかはお好みで。

頑張ってください。

[ ]
RE:10038 英語短縮表記への半角スペース追No.10041
でるもんたいいじま さん 22/12/30 09:51
 
こんにちは、秀丸愛用者の「でるもんた・いいじま」です。
スミマセン、訂正です。

> 今回はおそらく、
> replacedown "(Mstr|Sir|Mr|Mrs|Ms|Dr|Prof|Esq|Mx)\\.)", "\\1 ", regular, no
>casesense, nohilight ;
> で行けるはずです。

冒頭に開き括弧 '(' が抜けていました。

replacedown "((Mstr|Sir|Mr|Mrs|Ms|Dr|Prof|Esq|Mx)\\.)", "\\1 ", regular, noc
asesense, nohilight ;
としてください。

あるいは別解として、
replacedown "(Mstr|Sir|Mr|Mrs|Ms|Dr|Prof|Esq|Mx)\\.", "\\0 ", regular, nocas
esense, nohilight ;
でも行けると思います。

> あとは個人的には、最初からピリオドのあとにスペースが
> 入っている場合に余計なスペースを付け足さないように、
> replacedown "(Mstr|Sir|Mr|Mrs|Ms|Dr|Prof|Esq|Mx)\\.)\s*", "\\1 ", regular,
> nocasesense, nohilight ;
> と手直ししたくなりますが、この修正を入れるかどうかはお好みで。

こちらも同様です。それと、\s を \\s にしてください。
replacedown "((Mstr|Sir|Mr|Mrs|Ms|Dr|Prof|Esq|Mx)\\.)\\s*", "\\1 ", regular,
 nocasesense, nohilight ;
※こちらでは \\0 を使う別解は使えません。

失礼いたしました。

[ ]
RE:10041 英語短縮表記への半角スペース追No.10042
楽になりたい さん 22/12/30 15:35
 
でるもんた・いいじまさん。はじめまして。

> [...] の中に指定できるのは1文字単位の文字(あるいは a-z のような範囲指定)
>だけ

なるほど。そこを間違えていたんですね。

実は、試作マクロの変遷を調べてみると、ここは最初半角かっこなどの前後に半角ス
ペースを追加するループになっていたんです(一部抜粋)。

 $$target[ 0 ] = "([\\[\\(\\{&「<])" ;
 $$target[ 1 ] = "([\\]\\)\\}\\.\\?!&,」])" ;
 ##tc = 0 ;

 while( 2 > ##tc ) {

  gofiletop ;

  while( code != eof ) {

   searchdown2 $$target[ ##tc ], regular, nocasesense, nohilight ;
   if( false == result ) break ;

//   中略

   if ( 0 == ##tc) replacedown $$target[ ##tc ], " \\1", regular, nocasesens
e, nohilight ;
   else  replacedown $$target[ ##tc ], "\\1 ", regular, nocasesense, nohilig
ht ;

  }

  ##tc = ##tc + 1 ;

 }

その後に、短縮表記の後にも追加したい。ということで、メニューから試行錯誤した
結果を要素番号の1番に追加。

 $$target[ 1 ] = "([\\]\\)\\}&」>]|([(Mstr)|(Sir)|(Mr)|(Mrs)|(Ms)|(Dr)|(Prof)
|(Esq)|(Mx)]\\.))" ;

できちゃったじゃん! やった!
という事で大量のプレイリストを成型していたら、あれ? あれ? あれれ?
変な動きする時があるぞ!?
直らない!?

という訳で、アドバイスを頂きに参上した次第です。

次のように修正して、希望通りの動作になることを確認しました(一部抜粋)。

 $$target[ 1 ] = "([\\]\\)\\}&」>])" ;
 $$target[ 2 ] = "((Mstr|Sir|Mr|Mrs|Ms|Dr|Prof|Esq|Mx)\\.)" ;

 while( 3 > ##tc ) {

> 最初からピリオドのあとにスペースが入っている場合に余計なスペースを付け足さ
>ないように

こちらは一通りの処理後に、これをサブマクロとして呼び出している親マクロが

replaceallfast "[ ]+", " ", regular, nocasesense ;

で余分な空白文字を一括処理しています。
これならニュース記事などへの原文の引用文末のピリオド直後の半角スペースも残る
ので問題ないだろうと考えています。
ご指摘ありがとうございます。

今回はどうもありがとうございました。
助かりました。

また駆け込むことがあると思いますが、宜しくお願いします。

[ ]
RE:10042 英語短縮表記への半角スペース追No.10043
でるもんたいいじま さん 22/12/31 11:40
 
でるもんた・いいじまです・

無事解決したようで何よりです。
というわけで少々蛇足です。

ここの部分ですが、

>  $$target[ 0 ] = "([\\[\\(\\{&「<])" ;
>  $$target[ 1 ] = "([\\]\\)\\}\\.\\?!&,」])" ;
>  ##tc = 0 ;
>
>  while( 2 > ##tc ) {

while () の中にマジックナンバーの「2」を書かなくていい方法がいくつかあります
ので、参考までにご紹介します。

☆ ☆ ☆

ひとつは
while ( $$target[##tc] != "" )
とする方法。$$target[2] に何も入れていなければ秀丸マクロの場合、"" とみなさ
れます。

※ほかの言語だと必ずしもそうではないです。
perlなら
while ( $target[$tc] ne '' )
でも通りますし、
while ( defined $target[$tc] )
でも大丈夫ですが、C言語だと calloc() や memset() で初期化する、あるいは配列
の末尾に明示的に NULL を置く、そういった対応をしていないと痛い目にあいます。

☆ ☆ ☆

もうひとつは、初期化の段階で数を数える方法です。

##max = -1;
##max = ##max+1; $$target[ ##max ] = "([\\[\\(\\{&「<])" ;
##max = ##max+1; $$target[ ##max ] = "([\\]\\)\\}\\.\\?!&,」])" ;
//以下続く

##tc = 0 ;

while( ##tc <= ##max )  // 今回は '<=' になるので注意
{
//以下略

☆ ☆ ☆

以上、参考になれば幸いです。

[ ]
RE:10042 英語短縮表記への半角スペース追No.10044
でるもんたいいじま さん 22/12/31 11:55
 
でるもんた・いいじまです。
スミマセン、もうひとつ蛇足です。

>  while( 2 > ##tc ) {
> //   中略
>    if ( 0 == ##tc) replacedown $$target[ ##tc ], " \\1", regular, nocasese
>nse, nohilight ;
>    else  replacedown $$target[ ##tc ], "\\1 ", regular, nocasesense, nohil
>ight ;

ここの部分も、予め
$$from[0] = "([\\[\\(\\{&「<])" ; $$to[0] = " \\1" ;
$$from[1] = "([\\]\\)\\}\\.\\?!&,」])" ; $$to[1] = "\\1 ";
のようにしておいて、ループの中では単純に
replacedown $$from[##tc], $$to[##tc], regular, nocasesense, nohilight;
とすると、今後マクロが肥大化していったときにメンテナンスが楽になると思います。

それと、もし仮にnocasesense指定あり・なしの両方が必要になった場合には、上記
の $from[]、$to[] に加えて
##nocase[0] = 1;
##nocase[1] = 1;
のような指定を加えて、
if ( ##nocase[##tc] != 0 )
 replacedown $$from[##tc], $$to[##tc], regular, nocasesense, nohilight;
else
 replacedown $$from[##tc], $$to[##tc], regular, casesense, nohilight;
とすればOKです。

(複数のパラメータをまとめて数値で指定する方法もありますが、今回はそこまで複
雑ではないと思います。)

こちらもご参考までに。


[ ]