exl18の追加サンプル

2015/03/11

 exl18.exeは、rubyがインストールされていない環境で、exlap(Excel自動操縦用のrubyライブラリ)を使えるようにするため作った。

 このexl18で実行できるサンプルスクリプト(私が過去に作ったもの)を改めて眺めると、Excelの解説でよく取り上げられるSUM関数が出てこないなど、穴が少なくない。

 そこで、いくらかでも穴を埋めるべく、下に追加サンプルを記す。簡単な注釈を付けた程度で解説文はない。スクリプト中のコメントを参照されたい。

 追加サンプルは、exl_sample02.zipに同梱した。

 スクリプトの実行は Office2010 で試した。

 サンプルスクリプト sum01.rb を実行するなら、コマンドラインで次のように入力。

  exl18.exe sum01.rb [enter]

 exl21.exeでも実行可能。


《目次》


1. ExcelのSUM関数

 ExcelのSUM関数は、合計を求めるもの。あるセルに =SUM(B3:M3) と書き込んでおくと、B3:M3の合計値が表示される。

セル番地をA1形式で扱う場合

 下のスクリプトは、セル番地をA1とかB3のように記述している。分かりやすいが、素材データの行と列の数が変化した時に使えない。つまり柔軟性に欠ける。

−−−−−−−− sum01.rb ここから
# encoding: Windows-31J
  # 合計を求めるSUM関数の利用例
  # 素材:5つの支店の、1〜12月の売上げ台数
  # セル番地をA1形式で扱う。
require "exlap"

    # 素材データ(支店の売上げデータ、csvテキスト)
data_str = <<EOS
支店,月の売上げ台数
,1月,2月,3月,4月,5月,6月,7月,8月,9月,10月,11月,12月
池袋支店,113,118,144,50,135,113,104,57,54,96,72,136
上野支店,99,144,122,90,54,113,68,86,66,69,147,92
神田支店,104,127,133,126,139,111,55,83,105,79,103,65
品川支店,119,132,103,113,69,67,70,124,81,140,103,118
新宿支店,52,133,103,86,66,65,121,104,65,127,75,70
EOS
data_ary = Exl::str2ary(data_str, ",")  # csvをrubyの配列に変換

filename = "sum01.xls"
File.unlink(filename)  if test(?e, filename)  # 既に存在するなら削除
c_addr = %w(B C D E F G H I J K L M)  # 1〜12月の列番地
Exlap.new(filename) do |wb|
  ss = wb.ss(1)  # 第1ワークシートを選択
  ss.from_a(data_ary)  # 素材データを書き込む

      # 横方向(1〜12月)の合計欄を設ける
  ss.Range("N2").Value = "合計"
  for r in 3..7  # 各支店ごとに合計算出の関数を書き込む
    addr = "N#{r}"  # 第r行目の合計欄の番地(N3, N4など)
    rng = "B#{r}:M#{r}"  # 計算処理の対象範囲(B3:M3など)
    ss.Range(addr).Formula = "=SUM(#{rng})"
  end

      # 縦方向(池袋支店〜新宿支店)の合計欄を設ける
  ss.Range("A8").Value = "合計"
  c_addr2 = c_addr + ["N"]  # 各月の列に「合計」の列も加える
  for c in c_addr2  # 月ごとに合計算出の関数を書き込む
    addr = "#{c}8"  # 合計欄の番地(B8, C8など)
    rng = "#{c}3:#{c}7"  # 計算の対象範囲(B3:B7など)
    ss.Range(addr).Formula = "=SUM(#{rng})"
  end
  wb.save  # ワークブックの保存
end
−−−−−−−− sum01.rb ここまで

△ 目次に戻る


セル番地をRC形式で扱う場合

 下のスクリプトは、セル番地を RC[-12]:RC[-1] のような形式で記述している。

 また、行番号と列番号を数値として書き込むのでなく、変数に数値を代入した上で、その変数名を用いて記述するようにした。

 分かりにくいが、素材データの行と列の数が変化しても使える。

 前掲のsum01.rbと共通する素材データの定義部分を省略。

−−−−−−−− sum02.rb ここから
# encoding: Windows-31J
  # 合計を求めるSUM関数の利用例
  # 素材:5つの支店の、1〜12月の売上げ台数
  # セル番地をRC形式で扱う。
require "exlap"
  (中略)
Exlap.new(filename) do |wb|
  ss = wb.ss(1)  # 第1ワークシートを選択
  ss.from_a(data_ary)  # 素材データを書き込む
  tcell = ss.findf(/^\d+\.0$/)  # 最初の数値セル(売上げデータのセル)
  start_r, start_c = Exl::rc(tcell)  # tcellの番地を行番号・列番号で得る
  last_r, last_c = ss.range_last  # 最後(右下)のセルの番地

      # 横方向(1〜12月)の合計欄を設ける
  ss.cell(start_r-1, last_c+1).Value = "合計"
  nn = last_c - start_c + 1  # 列データの個数(1〜12月の12個)
  for r in start_r..last_r  # 各支店ごとの合計欄
    rng = "RC[#{-nn}]:RC[-1]"
    ss.cell(r, last_c+1).Formula = "=SUM(#{rng})"
  end

      # 縦方向(池袋支店〜新宿支店)の合計欄を設ける
  ss.cell(last_r+1, start_c-1).Value = "合計"
  nn = last_r - start_r + 1  # 行データ(支店)の個数:5つ
  for c in start_c..(last_c+1)  # 月ごとに合計算出の関数を書き込む
    rng = "R[#{-nn}]C:R[-1]C"  # → R[-5]C:R[-1]C
    ss.cell(last_r+1, c).Formula = "=SUM(#{rng})"
  end
  wb.save  # ワークブックの保存
end
−−−−−−−− sum02.rb ここまで

 「ss.findf(/^\d+\.0$/)」は、最初の数値セルを探索するもの。引数の正規表現は、123.0などの小数点数とマッチする。

 素材データには整数値しか出てこないが、Excelでは整数値も小数点数(float)として保持される。そのため先のような正規表現を用いた。

△ 目次に戻る


3ヶ月単位の合計(四半期の値)を別のワークシートに書き出す

 第1ワークシートに素材表を書き込み、第2ワークシートには3ヶ月単位の合計値を書き込む。つまり、1〜3月, 4〜6月, 7〜9月, 10〜12月の四半期の集計。

 第2ワークシートに焦点が当たっているとき、「Range("A1").Value = "=Sheet1!A1"」と書けば、A1欄に第1ワークシートのA1欄の値が入るが、この記述方法を利用する。

−−−−−−−− sum03.rb ここから
# encoding: Windows-31J
  # 合計を求めるSUM関数の利用例
  # 素材:5つの支店の、1〜12月の売上げ台数
  # 3ヶ月単位の合計(四半期の値)を別のワークシートに書き出す
require "exlap"
  (中略)
filename = "sum03.xls"
File.unlink(filename)  if test(?e, filename)  # 既に存在するなら削除
Exlap.new(filename) do |wb|
  ss = wb.ss(1)  # 第1ワークシートを選択
  ss.from_a(data_ary)  # 素材データを書き込む
  tcell = ss.findf(/^\d+\.0$/)  # 最初の数値セル(売上げデータのセル)
  start_r, start_c = Exl::rc(tcell)  # tcellの番地を行番号・列番号で得る
  last_r, last_c = ss.range_last  # 最後(右下)のセルの番地
  ss.cell(start_r-1, last_c+1).Value = "合計"
  for r in start_r..last_r  # 各支店の年間売上げ台数を算出
    ss.cell(r, last_c+1).Formula = "=SUM(RC[-12]:RC[-1])"
  end
  ss.range_autofit  # セル幅の自動調整

      # 第2ワークシートに四半期単位の値を書き出す
  ss = wb.ss(2)  # 第2ワークシートを選択
  ss.Range("A1:B1").Value = "支店", "四半期ごとの売上げ台数"
  ss.Range("B2:F2").Value = "1〜3月", "4〜6月", "7〜9月", "10〜12月", "合計"
  unit = 3  # 3ヶ月を1つの単位に
  for r in start_r..last_r  # 四半期ごとの売上げ台数を書き込む
    ss.cell(r,1).Formula = "=Sheet1!RC"  # 支店名を書き込む
    c = 2  # 台数を書き込む列番号
    start_c.step(last_c, unit) do |c1|  # 2:1月, 5:4月, 8:7月, 11:10月
      ss.cell(r,c).Formula = "=SUM(Sheet1!RC[#{c1-c}]:" +
          "Sheet1!RC[#{c1-c+unit-1}])"
      c += 1
    end
    ss.cell(r,c).Formula = "=SUM(RC[#{-(unit+1)}]:RC[-1])"
  end
  ss.range_autofit  # セル幅の自動調整
  wb.save
end
−−−−−−−− sum03.rb ここまで

 念のため、第1ワークシート、第2ワークシートの両方で年間の売上げ台数合計を算出している。これが食い違うようだと、どこかに誤りがあることになる。

△ 目次に戻る


2. ExcelのVLOOKUP関数

 VLOOKUP関数は、表の中から目的のデータを探り当てるための関数。まず表の左端を縦に検索し、該当のものがみつかったら横方向を辿っていくイメージ。引数は次のとおり。

 VLOOKUP(検索値, 処理対象範囲, 注目列番号, 検索の型)

 素材表の左端の列から「検索値」(数値や文字)とマッチするものを探し、「処理対象範囲」(A4:C9など)の中の「注目列番号」のセルの値を返す。「注目列番号」は、素材表の中で何番目の列かを示す数。セルの絶対番地の列数ではない。

 「検索の型」にはFalse(完全一致方式)とTrue(近似値方式)を指定できる。「検索値」を探索する時の方式。

VLOOKUP関数の基本的な例

 「商品コード, 品名, 価格」の3列からなる表の中から、商品コード3の情報を検索して表示する。

−−−−−−−− vlookup01.rb ここから
# encoding: Windows-31J
  # ExcelのVLOOKUP関数の利用例
require "exlap"

    # 素材表の定義
data_str = <<EOS
商品コード,品名,価格
1,ラジオ,9800
2,テレビ,56800
3,CDコンポ,48800
4,ICレコーダ,12800
5,ヘッドフォン,8280
EOS
data_ary = Exl::str2ary(data_str, ",")  # 素材表をrubyの配列に変換

filename = "vlookup01.xls"
File.unlink(filename)  if test(?e, filename)  # 既に存在するなら削除
Exlap.new(filename) do |wb|
  ss = wb.ss(1)  # 第1ワークシートを選択
  start_cell = "A4"  # この番地以降に素材表を書き込む
  ss.from_a(start_cell, data_ary)  # 素材表をA4以降に書き込む
  rng = ss.Range(start_cell).CurrentRegion  # データのある領域
  addr = Exl::a1(rng)  # データのある領域の番地(A4:C9)
  ss.Range("A1").Value = "商品コード3の情報"
  ss.Range("A2").Value = "品名"
  ss.Range("B2").Formula = "=VLOOKUP(3, #{addr}, 2, False)"
  ss.Range("C2").Value = "価格"
  ss.Range("D2").Formula = "=VLOOKUP(3, #{addr}, 3, False)"
  wb.save
end
−−−−−−−− vlookup01.rb ここまで

 上のスクリプトでは、素材表の始点をA4にしているが、B4とかC5など他の番地に変更しても問題ない。VLOOKUP()の引数を変更する必要はない。

△ 目次に戻る


別のワークシートの「名前付き範囲」を素材表にしてVLOOKUPを用いる

 素材表が第1ワークシートにあり、VLOOKUPの結果を第2ワークシートに表示する例を掲げる。素材表を「名前付き範囲」として定義する。

−−−−−−−− vlookup02.rb ここから
# encoding: Windows-31J
  # ExcelのVLOOKUP関数の利用例
  # 「商品コード,品名,価格」の表から商品コード3の情報を検索して表示
  # 別のワークシートの「名前付き範囲」を素材表にしてVLOOKUPを用いる
require "exlap"

    # 素材表の定義
data_str = <<EOS
商品コード,品名,価格
1,ラジオ,9800
2,テレビ,56800
3,CDコンポ,48800
4,ICレコーダ,12800
5,ヘッドフォン,8280
EOS
data_ary = Exl::str2ary(data_str, ",")  # 素材表をrubyの配列に変換

filename = "vlookup02.xls"
File.unlink(filename)  if test(?e, filename)  # 既に存在するなら削除
Exlap.new(filename) do |wb|
  ss = wb.ss(1)  # 第1ワークシートを選択
  ss.from_a(data_ary)  # 素材表をA1以降に書き込む
  rng = ss.UsedRange  # データが書き込まれている領域全体
  rng.Name = "価格表"  # 「名前付き範囲」の定義

  ss = wb.ss(2)  # 第2ワークシートを選択
  ss.Range("A1").Value = "商品コード3の情報"
  ss.Range("A2").Value = "品名"
  ss.Range("B2").Formula = "=VLOOKUP(3, 価格表, 2, False)"
  ss.Range("A3").Value = "価格"
  ss.Range("B3").Formula = "=VLOOKUP(3, 価格表, 3, False)"
  wb.save
end
−−−−−−−− vlookup02.rb ここまで

 素材表が書かれている領域に「価格表」という名前を付けた。セル番地でいうと A1:C6 だが、「価格表」という名前には、単にセル番地だけでなく、第1ワークシートにあるとの情報も付加されているらしい。

 「=VLOOKUP(3, 価格表, 3, False)」のように、ワークシートの情報を指定することなく引数を記述できるのは、そのためだと思われる。

 ちなみに、「価格表」の箇所をセル番地で記述するなら「Sheet1!A1:C6」とする。Sheet1はワークシート名。

 素材表が別のワークブック、例えば data.xls にある場合は、「[data.xls]Sheet1!A1:C6」とする。

 ここには掲げないが、素材表が別のワークブックにあるケースのスクリプト vlookup02b.rb を圧縮ファイルに同梱した。

△ 目次に戻る


2つの素材表を組み合わせて結果を得る

 先述の「価格表」の他に、商品の注文状況を示す素材表もあるものとする。「発注者, 商品コード, 注文個数」からなる表。

 2つの素材表から、発注者ごとにその発注者の氏名、注文の品名、単価、注文個数、請求額を示す表を作る。

 2つの素材表は第1ワークシートと第2ワークシートにあり、新たに作る表を第3ワークシートに置く。

−−−−−−−− vlookup03.rb ここから
# encoding: Windows-31J
  # ExcelのVLOOKUP関数の利用例
  # 2つの素材表(価格表、注文票)から第3の表を作成
  # 発注者ごとに請求額を算出した表を作る
require "exlap"

    # 素材表その1の定義
data1_str = <<EOS
商品コード,品名,価格
1,ラジオ,9800
2,テレビ,56800
3,CDコンポ,48800
4,ICレコーダ,12800
5,ヘッドフォン,8280
EOS
data1_ary = Exl::str2ary(data1_str, ",")  # 素材表をrubyの配列に変換

    # 素材表その2の定義
data2_str = <<EOS2
発注者,商品コード,注文個数
鈴木,3,2
高橋,1,5
渡辺,4,2
佐藤,2,3
井上,5,4
EOS2
data2_ary = Exl::str2ary(data2_str, ",")

filename = "vlookup03.xls"
File.unlink(filename)  if test(?e, filename)  # 既に存在するなら削除
Exlap.new(filename) do |wb|
  ss = wb.ss(1)  # 第1ワークシートを選択
  ss.from_a(data1_ary)  # 素材表をA1以降に書き込む
  rng = ss.UsedRange  # データが書き込まれている領域全体
  rng.Name = "価格表"  # 「名前付き範囲」の定義

  ss = wb.ss(2)  # 第2ワークシートを選択
  ss.from_a(data2_ary)  # 素材表をA1以降に書き込む
  rng = ss.UsedRange  # データが書き込まれている領域全体
  rng.Name = "注文表"  # 「名前付き範囲」の定義

  ss = wb.ss(3)  # 第3ワークシートを選択
  ss.from_a(%w(発注者 品名 単価 注文個数 請求額))  # 見出しの書き込み
  rng = wb.Application.Range("注文表")  # 改めて「注文表」を取得
  orders = rng.Value  # 注文表の中身を2次元配列で得る
  orders.shift  # 見出しを取り除く
  rn = 2  # 第3ワークシートにおいて書込みを行う行の番号
  orders.each do |row|  # 注文表の中身を1行づつ取り出す
    ss.cell(rn,1).Value = row[0]  # 発注者の氏名
    ss.cell(rn,2).Formula = "=VLOOKUP(#{row[1]}, 価格表, 2, False)"  # 品名
    ss.cell(rn,3).Formula = "=VLOOKUP(#{row[1]}, 価格表, 3, False)" # 単価
    ss.cell(rn,4).Value = row[2]  # 注文個数
    ss.cell(rn,5).Formula = "=RC[-2]*RC[-1]"  # 請求額
    rn += 1  # 次に書込みを行う行の番号
  end
  wb.save
end
−−−−−−−− vlookup03.rb ここまで

 ここには掲げないが、2つの素材表が別のワークブック data.xls にあり、それぞれ「名前付き範囲」として定義されているケースのスクリプト vlookup03b.rb を圧縮ファイルに同梱した。

 別のワークブックの素材表を取得するには「rng = wb.Application.Range("data.xls!注文表")」のようにする。

 VLOOKUP関数の引数は「=VLOOKUP(3, data.xls!価格表, 2, False)」のように書く。

△ 目次に戻る


3. Excelの日付・時刻の扱い

 Excelでは日付・時刻がシリアル値で保持される。この値は1900年1月1日午前0時を1とする値。半日経過すると0.5だけ増える。

 時刻だけのデータは、1未満のシリアル値になる。午前0時から1時間経過するごとに、24分の1(0.041666)だけ増える。

出社時刻と退社時刻から勤務時間と給与を算出

 日付、出社時刻、退社時刻の3項目からなる素材表がある。これに勤務時間と給与日額を付加する。給与は、時給900円で計算。

−−−−−−−− date_time01.rb ここから
# encoding: Windows-31J
require "exlap"

data_str = <<EOS
日付,出社時刻,退社時刻
01/05,09:00,17:00
01/06,08:45,17:15
01/07,08:30,16:50
EOS
data_ary = Exl::str2ary(data_str, ",")

filename = "date_time01.xls"
File.unlink(filename)  if test(?e, filename)
Exlap.new(filename) do |wb|
  ss = wb.ss(1)  # 第1ワークシートを選択
  ss.from_a(data_ary)  # 素材表をA1以降に書き込む
  last_r, last_c = ss.range_last  # 素材表の最終番地
  ss.Range("D1:E1").Value = "勤務時間", "給与"  # 見出しの書込み
  for r in 2..last_r  #各日付ごとに、勤務時間と給与を算出
    ss.cell(r, last_c+1).Formula = "=RC[-1]-RC[-2]"
    ss.cell(r, last_c+2).Formula = "=RC[-1]*24*900"
  end
  wb.save
end
−−−−−−−− date_time01.rb ここまで

 関数「time(時間,分,秒)」を用いると「time(1,0,0)」により、1時間がシリアル値でどれくらいになるかを算出できる。

 なので、「給与」の算出式を次のように書くこともできる。

=RC[-1]/time(1,0,0)*900

勤務が午前様になる場合への対処

 出社時刻が「09:00」、退社時刻が翌日になってしまい「00:30」だと、先のスクリプトでは正しい値を算出できない。

 退社時刻が翌日になった時はシリアル値を1だけ増やす必要がある。IF関数を使ってそれに対処したのが下のスクリプト。24時間以上続けて働くことはないとの前提に立つ。

−−−−−−−− date_time02.rb ここから
# encoding: Windows-31J
require "exlap"

data_str = <<EOS
日付,出社時刻,退社時刻
01/05,09:00,17:00
01/06,08:45,17:15
01/07,08:30,16:50
01/08,09:00,00:30
01/09,10:00,00:50
EOS
data_ary = Exl::str2ary(data_str, ",")

filename = "date_time02.xls"
File.unlink(filename)  if test(?e, filename)
Exlap.new(filename) do |wb|
  ss = wb.ss(1)  # 第1ワークシートを選択
  ss.from_a(data_ary)  # 素材表をA1以降に書き込む
  last_r, last_c = ss.range_last  # 素材表の最終番地
  ss.Range("D1:E1").Value = "勤務時間", "給与"  # 見出しの書込み
  hours = "=IF(RC[-2]<=RC[-1], RC[-1]-RC[-2], RC[-1]+1-RC[-2])"
  for r in 2..last_r  #各日付ごとに、勤務時間と給与を算出
    ss.cell(r, last_c+1).Formula = hours
    ss.cell(r, last_c+1).NumberFormatLocal = "h:mm"
    ss.cell(r, last_c+2).Formula = "=RC[-1]/time(1,0,0)*900"
  end
  wb.save
end
−−−−−−−− date_time02.rb ここまで

 IF関数で計算すると、シリアル値の表示形式が「時刻」ではなく通常の「数値」になってしまう。そのためNumberFormatLocalを設定して「時刻」の表示になるよう調整している。

曜日による給与の割り増し計算(WEEKDAY関数)

 土曜・日曜に勤務した場合、時給を1.3倍にするものとする。

 ExcelのWEEKDAY関数は、第1引数の日付の曜日を1〜7の数値で返す。第2引数を省略すると、日曜:1 …… 土曜:7になるので、第2引数に2をセットして、月曜:1 …… 日曜:7になるようにする。

−−−−−−−− date_time03.rb ここから
# encoding: Windows-31J
  # 日付と時刻を扱う例:WEEKDAY関数で曜日を扱う
require "exlap"

data_str = <<EOS
日付,出社時刻,退社時刻
01/05,09:00,17:00
01/06,08:45,17:15
01/07,08:30,16:50
01/08,09:00,00:30
01/09,10:00,00:50
01/10,09:00,17:00
01/11,08:45,17:15
EOS
data_ary = Exl::str2ary(data_str, ",")

filename = "date_time03.xls"
File.unlink(filename)  if test(?e, filename)  # 既に存在するなら削除
Exlap.new(filename) do |wb|
  ss = wb.ss(1)  # 第1ワークシートを選択
  ss.from_a(data_ary)  # 素材表をA1以降に書き込む
  last_r, last_c = ss.range_last  # 素材表の最終番地
  ss.Range("D1:E1").Value = "勤務時間", "給与"  # 見出しの書込み
  hours = "=IF(RC[-2]<=RC[-1], RC[-1]-RC[-2], RC[-1]+1-RC[-2])"
  pay = "=IF(WEEKDAY(RC[-4],2)<6, RC[-1]*24*900, RC[-1]*24*900*1.3)"
  for r in 2..last_r  # 各日付ごとに、勤務時間と給与を算出
    ss.cell(r, 1).NumberFormatLocal = "yyyy年m月d日(aaa)"
    ss.cell(r, last_c+1).Formula = hours
    ss.cell(r, last_c+1).NumberFormatLocal = "h:mm"
    ss.cell(r, last_c+2).Formula = pay
    ss.cell(r, last_c+2).NumberFormatLocal = "#0"  # 整数として表示
  end
  ss.range_autofit  # セル幅の自動調整
  wb.save
end
−−−−−−−− date_time03.rb ここまで

△ 目次に戻る


時刻の記入がない場合への対処(CELL関数)

 出社時刻または退社時刻の欄に記入がない場合、あるいは「休暇」などの文字が書き込まれている場合に、勤務時間と給与の欄を空欄にするスクリプトを掲げる。

 セルに書き込まれているデータのタイプを知るのにCELL関数を用いる。TYPE関数でもデータのタイプを知ることができるが、こちらは戻り値が数値と空欄が同じ1になるので今回は採用しなかった。

 「CELL("type",A1)」とすると、A1欄が空欄ならb, 文字ならl, 数値だとvを返す。日付・時刻はシリアル値(つまり数値)なのでv。

 下は、先の date_time03.rb を少し書き換えただけだが、IF関数が入れ子になり少々ややこしい。

−−−−−−−− date_time04.rb ここから
# encoding: Windows-31J
  # 日付と時刻を扱う例:時刻の欄が空欄や文字の場合に対処
  # CELL関数でセルに書き込まれているデータのタイプを取得
require "exlap"

data_str = <<EOS
日付,出社時刻,退社時刻
01/05,09:00,
01/06,,17:15
01/07,08:30,16:50
01/08,休暇,
01/09,10:00,00:50
01/10,09:00,17:00
01/11,08:45,17:15
EOS
data_ary = Exl::str2ary(data_str, ",")

filename = "date_time04.xls"
File.unlink(filename)  if test(?e, filename)  # 既に存在するなら削除
Exlap.new(filename) do |wb|
  ss = wb.ss(1)  # 第1ワークシートを選択
  ss.from_a(data_ary)  # 素材表をA1以降に書き込む
  last_r, last_c = ss.range_last  # 素材表の最終番地
  ss.Range("D1:E1").Value = "勤務時間", "給与"  # 見出しの書込み
  cond = 'OR(CELL("type",RC[-2])<>"v",CELL("type",RC[-1])<>"v")'
  calc = 'IF(RC[-2]<=RC[-1], RC[-1]-RC[-2], RC[-1]+1-RC[-2])'
  hours = "=IF(#{cond},\"\",#{calc})"
  calc = "IF(WEEKDAY(RC[-4],2)<6, RC[-1]*24*900, RC[-1]*24*900*1.3)"
  pay = "=IF(#{cond},\"\",#{calc})"
  for r in 2..last_r  # 各日付ごとに、勤務時間と給与を算出
    ss.cell(r, 1).NumberFormatLocal = "yyyy年m月d日(aaa)"
    ss.cell(r, last_c+1).Formula = hours
    ss.cell(r, last_c+1).NumberFormatLocal = "h:mm"
    ss.cell(r, last_c+2).Formula = pay
    ss.cell(r, last_c+2).NumberFormatLocal = "#0"  # 整数として表示
  end
  ss.range_autofit  # セル幅の自動調整
  wb.save
end
−−−−−−−− date_time04.rb ここまで

 rubyに慣れていると、不等号を ‘!=’ と書いてしまいがちだが、Excelでは ‘<>’ と書くので注意(自戒をこめて)。


 番外編として nhk_headers.rb をアップロードしておくので、よかったら試されたい。

 NHKのニュースサイトにアクセスし、見出しの一覧を取得。それをExcelにハイパーリンクの形で書き込む。見出しの本文を読みたい時は、Excelで該当のハイパーリンクを開けばよい。

 NHKのサイトの掲載方法が変更されると使えなくなるかもしれないが、2015年3月11日現在は大丈夫。


〜 以上 〜

(ExcelだけでなくMS-Word関連その他のサンプルスクリプトも追加したいと思っているが、とりあえず今回は終了。)