特殊文字を一括変換

HTMLファイルのソースをホームページなどで公開するとき、面倒なのがタグの<>を変換することです。
で、BATファイルを使って何とかできないかと思って作りました。ソースはこちらです。

用途↓
HTMLファイルのソースをホームページなどで公開したいとき、<>を文字コードに変換する手間を省きます。
公開用のソースは、テキストファイル形式(拡張子:.txt)で控えフォルダに保存されます。
複数のファイルがあるとき、下のbatファイルが置かれたフォルダ内のすべてのHTMLファイルを一括に変換します。
更新したHTMLも、このファイルをワンクリックするだけで一括に内容を変換します。

使い方↓
1:ソースをコピーして、適当な名前を付けて、
変換したいHTMLファイルがあるフォルダに、
拡張子を.batにして保存してください。 例:kakikae.bat

2:HTMLファイルがあるフォルダ内に控えという名前のフォルダを作ってください。

3:HTMLファイルを作ったら、batファイルをクリックしてください。

上のリンクに、ソースと、元のHTMLファイル、変換後のテキストファイルの内容を載せていますので、必要な方はご覧ください。

なお、JAVASCRIPTなどで書くは、変換の対象から省く設定にしています。

かなり便利なテキストエディタ TERAPAD

文章を書くとき、マイクロソフトのワードや、OpenOfficeのWriterを使うのが多いかと思いますが、テキストエディタを使うのも、悪くありません。
テキストエディタで文章を作り、ファイルを保存する作業を行うことのメリットは、ざくっとリストアップしてみると次のようになります。

  1. 起動が速い。
  2. 動作がさくさく動く。
  3. 見栄えにとらわれることなくシンプルな文章を作成できる。ワードやWRITERを重宝に感じるのは、文章や見栄えを装飾する必要があるときでしょう。僕の場合は、あまりその必要がないのでテキストエディタのシンプルさにメリットを感じます。
  4. 出来上がりのファイルが超軽量級。約3500文字の日本語ばかりの文章を作って保存した場合、テキストファイルなら3.45KB。DOCファイルなら12.5KB、ODTファイルなら9.16KBです。ファイルサイズを比較するには、SKYDRIVEからファイルサイズ比較(ZIPファイル)をダウンロードしてください。
  5. ファイルのやり取りをするとき、先方のOSのバージョンや、Officeソフトの種類、バージョンを気にせずにすむ。

主には、こんなところでしょうか?

ただ、テキストエディタの代表格である、WINDOWSに付属しているメモ帳はただ単に文章を書いて保存できるだけのソフトウェアで、あまりにも愛想がありません。
そこで、いろいろ便利に使えて愛想もあってそして無料のテキストエディタの、をこれから紹介していきたいと思います。

僕がいつも使っているテキストエディタTERAPADです。



TERAPADを使っていて、良いなあと思うのは、まず何をおいても軽快に動くことです。今この記事を書いているパソコンはWIN7でメモリを3ギガ積んでいるのでまあまあOFFICEソフトでも軽快ですが、他、WINXPパソコンはメモリを512メガしか積んでいません。このスペックでOFFICEソフトを起動させるとき、ちょっとイラッと来ることもないとはいえません。
というのは、XPパソコンは、ほとんどお遊び用なので外付けの機器やドライブやらの線もつないであって、またいろんなファイルも保存してあるので起動しているだけでいっぱいいっぱいという状況なのです。ま、それはうちの事情ですが、それでもTERAPADは軽快に立ち上がって働いてくれます。

というようなことで、これからTERAPADの使い方(僕なりの)をここで書きたいと思いますので、宜しければお付き合いください。

OpenOfficeで表示対象の社員のIDを絞り込む

下の表は、A列に社員のIDが入力されています。
IDの一部分をE2セルに入力すれば、その候補がE-G列に表示されるシステムを関数を使って作ってみました。

まず左端の一文字を打ち込みます。10人の候補が表示されました。

送信者 OpenOffice
4文字を打ち込むと↓↓↓↓↓↓↓↓ 6人に絞り込まれました。
送信者 OpenOffice
このファイルはSKYDRIVEからcalc165.odsをダウンロードしてください。

D列の説明

D列では、E2セルに入力された文字数分を、A列のそれぞれのIDの左側から取り出しています。
=LEFT(A2;LEN($E$2))
ここで取り出された文字列が評価の対象になります。

F2セルの説明

ここでは、E2セルに入力された文字分と一致するのが、D列に何個あるかを数えています。
=COUNTIF(D2:D300;E2)
ここでF2セルの書式設定を文字列にしておく必要があります。
送信者 OpenOffice
D列の説明で書いた関数の組み合わせを使って文字列を取り出すと、数字も文字列として取り出されてしまいます。
D列とE2セルの書式を一致させないと、正しく判定されません。これを回避するための措置です。

E3からG3セルの説明

A1からC1セルとタイトルを同じにしておきます。
こうすることでE列:G列の4行目以降の関数の組み立てがシンプルになります。

E列:G列の4行目以降の説明

=IF(COUNTA($E$4:E4)<=$F$2;INDIRECT(ADDRESS(MATCH($E$2;INDIRECT(ADDRESS(MATCH(E3;$A$1:$A$300;0)+1;4)):$D$300;0)+MATCH(E3;$A$1:$A$300;0);1));"")
シンプルにと言ってもこんなに長いのですが、構造は意外にシンプルです。
=IF(COUNTA($E$4:E4)<=$F$2;処理;"")
E4セルでは、F2セルに表示されている該当セルの個数よりもE4:E4セルの間の空白ではないセルの個数の数が同じか、あるいは少なければ処理を行ない、それ以外のときは空白にしておくという数式です。

E列:G列の4行目以降で処理を行なう場合の説明

=MATCH($E$2;INDIRECT(ADDRESS(MATCH(E3;$A$1:$A$300;0)+1;4)):$D$300;0)
この数式で、E2セルの値がADDRESS(MATCH(E3;$A$1:$A$300;0)+1;4):$D$300の間で最初に登場するのは何行目かを求めます。
ここで、ADDRESS(MATCH(E3;$A$1:$A$300;0)+1;4)は、E3セルに入力されている値が、A列で何行目に登場しているかを求めてその一行下のアドレスを返させています。
E4セルの場合、一行上のセルには"ID"が入力されていて、A列では一行目に現れるので、2行目から300行目までの間でE2セルに入力されている値が最初に登場するセルの行番号を返すことになります。この結果2が返されます。

=MATCH(E3;$A$1:$A$300;0)
ここで、E3セルの値が現れたセルの行番号を返させています。E4セルの場合、一行上のセルには"ID"が入力されていて、A列では一行目に現れるので、1が返されます。
2+1の結果である3がE4セルに返されるべきセルの値があるA列の行番号になります。

列は、IDが入力されている一列目なので1を当てはめ、ADDRESS関数とINDIRECT関数をかぶせて数式を完成させます。
=INDIRECT(ADDRESS(MATCH($E$2;INDIRECT(ADDRESS(MATCH(E3;$A$1:$A$300;0)+1;4)):$D$300;0)+MATCH(E3;$A$1:$A$300;0);1))

F4セルの場合はADDRESS関数に当てはめる列番号を2にします。G4セルの場合はADDRESS関数に当てはめる列番号を3にします。それ以外はE列と全く同じです。


E5セルの場合を例にとってもう一度処理してみましょう。
=IF(COUNTA($E$4:E5)<=$F$2;INDIRECT(ADDRESS(MATCH($E$2;INDIRECT(ADDRESS(MATCH(E4;$A$1:$A$300;0)+1;4)):$D$300;0)+MATCH(E4;$A$1:$A$300;0);1));"")

E2セルの値が、ADDRESS(MATCH(E4;$A$1:$A$300;0)+1;4):$D$300の間で最初に現れるセルの行番号を求めます。
ここでMATCH(E4;$A$1:$A$300;0)+1によってひとつ上の行のE4セルの値が現れる行番号を求め、その一行下のD列のセルをMATCH関数での検索の起点にします。
ここではD4セルが、検索の起点になります。
MATCH($E$2;$D$4:$D$300;0)で D4セルから数えて4行下に該当の行があるので、MATCH(E4;$A$1:$A$300;0)で得られる、先にE4の値が現れた行番号3を加えて7がADDRESS関数に当てはめられる行番号になります。

OpenOfficeでセルを範囲選択するとき、キーボードを使うと楽になる F8キー

F8キーで便利になるセル選択

F8キーを押して、↑↓←→を押すと、セルを範囲選択するとき楽になります。
起点にしたいセルを選択してF8キーを
押してから↑↓←→を押すと、起点から上下左右のセルを簡単に選択できます。


選択を終了したいときはもう一度F8キーを押します。


A2セルを起点にしたいのでA2セルを選択してF8キーを押す

送信者 OpenOffice

→キーで右側に選択範囲を広げる

送信者 OpenOffice

→キーでもうちょっと右まで広げてみる

送信者 OpenOffice

↓キーで下に選択範囲を広げる

送信者 OpenOffice

選択範囲を広げすぎたので↑←キーを押して選択範囲を縮小する

送信者 OpenOffice

選択が終了したらF8キーをもう一度押して、選択範囲の上で右クリックすると書式の変更、削除、などなど何でもできます。



Shiftキーを使うともっと便利になる

F8キーで起点のセルを選択後、Shiftキーを押してセルを選択すると選択したセルが選択範囲の終点になります。

  1. A2セルを選択 F8キーを押す・・・起点が選択された
  2. Shiftキーを押してE16セルを選択・・・終点が選択された
  3. もう一度F8キーを押して選択処理終了

OpenOfficeで北部エリアに何個の支店があるかを調べる

同じ支店名が何回も登場したり、一回しか登場しないものもあったりして、いったいいくつの支店があるんだと思って数えていたら、いつの間にかほかのエリアのものを数えていたりという経験、あるのは私だけでしょうか。

送信者 OpenOffice
このファイルはSKYDRIVEからcalc164.odsをダウンロードしてください。

そんな間違い、イライラを防止するには、SUMPRODUCT関数を使って、下のようにしては如何でしょう?

送信者 OpenOffice

この数式では、L1:L12の値をB1:B300の範囲のなかから、MATCH関数で検索します。
MATCH($L$1:$L$12;$B$1:$B$300;0)

このプロセスで、該当する行を発見したら、その行のA列の値を返すようにADDRESS関数とINDIRECT関数で処理します。
INDIRECT(ADDRESS(MATCH($L$1:$L$12;$B$1:$B$300;0);1))

INDIRECT関数で返された値が、I2セルと同じであれば1を加えるという意味の数式です。

エリア名を抜き出す方法と、支店名を抜き出す方法は、「 営業成績表から支店名を抜き出すには 」
をご覧ください。

営業成績表から支店名を抜き出すには

全部で47人の社員がいて、エリアごとに管理された営業拠点に所属しています。
さて、いったいいくつの営業拠点があるのか、一つずつ抜き出してみればいいのでしょうが、手で抜き出すのは、結構面倒です。
そんなときは、こうしては如何でしょうか?

送信者 OpenOffice
このファイルはSKYDRIVEからcalc164.odsをダウンロードしてください。

まずは、エリア名を抜き出してみます。-上の画像のI2セルの場合↓↓↓↓↓

=INDIRECT(ADDRESS(MATCH(I1;$A$1:$A$301;0)+COUNTIF($A$1:$A$301;I1);1))
の数式の処理結果として、I2セルに北部を返しています。
この数式では、I2セルのひとつ上のセル(ここではI1セル)の値が表のA列の何行目から始まっているかを求めて
=MATCH(I1;$A$1:$A$300;0)

I1セルの値がA1:A300 の範囲内に何個あるかを数えます。
=COUNTIF($A$1:$A$300;I1)

I2セルでの処理の場合、ひとつ上のI1セルには「エリア」が入っています。
「エリア」は、A列で1行目から始まっていて、一個だけあります。
ここで1+1=2より、2をADDRESS関数に当てはめます。エリア名が入力されているA列を処理対象にするので、ADDRESS関数に組みいれる列番号は1にします。
=ADDRESS(MATCH(I1;$A$1:$A$300;0)+COUNTIF($A$1:$A$300;I1);1)
これで$A$2がADDRESS関数の処理結果として返されるので、INDIRECT関数に当てはめて、A2セルの値「北部」を表示させます。
=INDIRECT(ADDRESS(MATCH(I1;$A$1:$A$300;0)+COUNTIF($A$1:$A$300;I1);1))



子供だましのような?
と思われてしまう方のために、I3セルを例にとってもう一度説明します。
=INDIRECT(ADDRESS(MATCH(I2;$A$1:$A$300;0)+COUNTIF($A$1:$A$300;I2);1))
I2セルの値が、A1:A300の範囲内で何行目から始まっているかをMATCH関数を使って調べ、ここでは2が返されます。
I2セルの値がA1:A300の範囲内で何個あるかを数えます。ここでは20が返されます。
2と20を足すと22になるので、この値をADDRESS関数の行番号として、列番号を1として、=ADDRESS(22;1) で$A$22 が返されます。これをINDIRECT関数に当てはめると、A22セルの値「中部」がI3セルに返されます。



同様にして、支店名を抜き出してみましょう。

送信者 OpenOffice
L2セルの場合↓↓↓↓↓
=INDIRECT(ADDRESS(MATCH(L1;$B$1:$B$301;0)+COUNTIF($B$1:$B$301;L1);2))

仕組みは、エリアを抜き出したときとまったく同じです。
L2セルのひとつ上のセル(ここではL1セル)の値が表のB列の何行目から始まっているかを求めて
=MATCH(L1;$B$1:$B$300;0)

L1セルの値がB1:B300 の範囲内に何個あるかを数えます。
=COUNTIF($B$1:$B$300;L1)


L2セルでの処理の場合、ひとつ上のI1セルには「支店名」が入っています。
支店名はB1:B300セルの中で1行目にあって、一個だけです。
ここで1+1=2より、2をADDRESS関数に当てはめます。支店名が入力されているB列を処理対象にするので、ADDRESS関数に組みいれる列番号は2にします。
=ADDRESS(MATCH(L1;$B$1:$B$300;0)+COUNTIF($B$1:$B$300;L1);2)
これで$B$2 が返されるので、これをINDIRECT関数に当てはめて
=INDIRECT(ADDRESS(MATCH(L1;$B$1:$B$300;0)+COUNTIF($B$1:$B$300;L1);2))
でL2セルに「北部第一支店」が返されます。

以下そのままコピー&ペーストです。




上の処理の結果で返されたエリアの中に、いくつの支店があるか数えたい というときは
「 OpenOfficeで北部エリアに何個の支店があるかを調べる 」をごらんください。

OpenOfficeで一つの表から支店内ランク、エリア内ランクを求める

下の表では、社員の売上金額に基づいて、全体のランクと併せて所属エリア内、所属支店のランクが表示されています。
全体のランクは、売上金額をRANK関数でD列の中で判定すればいいことですが、所属エリア内、所属支店でのランクをこの一つの表から求めるには、どうしたらいいでしょうか?

送信者 OpenOffice

答えは、これです。↓↓↓↓↓↓↓

送信者 OpenOffice
このファイルはSKYDRIVEからcalc163.odsをダウンロードしてください。

この表ではRANK関数を使って答えを出しています。
関数名:RANK関数
書式:=RANK(処理対象の値;範囲;タイプ)
何ができる:処理対象の値が範囲内で、何位かを判定してランクを返す。
平たく書くと:=RANK(D2;$D$2:$D$300;0) で、D2の値がD2:D300の範囲内で何位かを返します。
ここで、タイプを1に設定すると、値が小さいものを上位にランクさせることができます(昇順)。



支店内ランクの求め方

支店内ランクは、支店の行が何行目から始まって何行目まで続いているかを求めることがポイントになります。
そのためには、MATCH関数を使います。
関数名:MATCH関数
書式:=MATCH(処理対象の値;範囲;タイプ)
何ができる:処理対象の値が範囲内で、何番目に登場するかを数える。
平たく書くと:=MATCH("勝手なシンドバッド";C1:C45;0) で、勝手なシンドバッドがC1:C45の範囲内で11番目の行に登場することが分かります。
ここで、同じデータが複数登場する場合、タイプを0に設定すると、一番最初に登場する行を答えとして返します。



RANK関数の範囲の起点の設定



=MATCH(B2;$B$1:$B$300;0) でB2の値(北部第一支店)は2行目に初めて登場していることが分かります。

以上のプロセスで得られた値を行番号としてADDRESS関数に当てはめます。

判定の対象になる売上金額が入っている4列目をRANK関数内で範囲に設定したいので、ADDRESS関数に入れる列番号は4を入れます。
=ADDRESS(MATCH(B2;$B$1:$B$300;0);4)

これで、E2セルの場合、$D$2が返されるので、この値を数式の中で再計算の対象にできるように、INDIRECT関数に当てはめます。
=INDIRECT(ADDRESS(MATCH(B2;$B$1:$B$300;0);4))

ここまでで、RANK関数での判定範囲の起点が設定できました。



RANK関数の範囲の終点の設定


全体の範囲内に北部第一支店が何個登場するかを数えて、その値をMATCH関数で得られた値に加えて終点の行番号にすることにします。
=COUNTIF($B$1:$B$300;B2)+MATCH(B2;$B$2:$B$300;0)
ここで、MATCH関数の範囲の設定をB1からでなく、B2からにすると、最初に登場する行を除外して計算することができます。または、
=COUNTIF($B$1:$B$300;B2)+MATCH(B2;$B$1:$B$300;0)-1
で、同じ結果(ここでは6)が得られます。

MATCH関数で得られた値を、起点の時と同様にADDRESS関数に当てはめます。ここでも、ADDRESS関数に入れる列番号は4です。
さらにINDIRECT関数をかぶせて数式の中で使用できるようにします。
=INDIRECT(ADDRESS(COUNTIF($B$1:$B$300;B2)+MATCH(B2;$B$2:$B$300;0);4))

ここまでで、RANK関数での判定範囲の終点が設定できました。

これですべて材料が整ったので、RANK関数にすべてを当てはめてみましょう。
=RANK(D2;INDIRECT(ADDRESS(MATCH(B2;$B$1:$B$300;0);4)):INDIRECT(ADDRESS(COUNTIF($B$1:$B$300;B2)+MATCH(B2;$B$2:$B$300;0);4));0)

めでたく、河合菜穂子さんが北部第一支店内で1位であることが分かりました。




エリア内ランクの求め方

基本的な考え方は、支店内ランクと全く同じです。
支店内ランクでは、支店名が入力されているB列を範囲設定のときに処理対象にしていましたが、今度はエリアが入力されているA列を対象にすることにします。
それだけです。
=RANK(D2;INDIRECT(ADDRESS(MATCH(B2;$B$1:$B$300;0);4)):INDIRECT(ADDRESS(COUNTIF($B$1:$B$300;B2)+MATCH(B2;$B$2:$B$300;0);4));0)
を下のようにします。
=RANK(D2;INDIRECT(ADDRESS(MATCH(A2;$A$1:$A$300;0);4)):INDIRECT(ADDRESS(COUNTIF($A$1:$A$300;A2)+MATCH(A2;$A$2:$A$300;0);4));0)

なお、この表と数式を成立させるためには、エリア>支店名>社員名のルールに基づいて表が構成されている必要があります。
たとえば、北部の北野支店のデータが16行目でいったん終了して再び22行目から始まったりすると正確な結果を返しません。
この場合は再度並べ替える必要があります。
送信者 OpenOffice