プロが教えるわが家の防犯対策術!

Excel 2003 です。

2つ質問がありますが、2点とも稀なケースの問題ですので急いではおりません。
お時間のある時にでもアドバイスをいただければ幸いです。
よろしくお願いします。


【質問1】

日付が入力されているセルの個数をカウントしたいのですが

=COUNTIF(B2:B6,">=2006/04/01")

のように数式を記述すると期待通りの結果を求められます。
しかし、セル範囲の中に 38885 のような値を入力すると、そのセルも日付として
カウントしてしまいますよね。
そうなる理由は分かっているのですが、どういう数式を記述すればよいのかが
分かりません。


【質問2】

上記課題を解決できないのでユーザー定義関数を自作しました。

Public Function CountDate(範囲 As Range) As Long
  Dim MyCount As Long
  Dim MyRange As Range
  MyCount = 0
  For Each MyRange In 範囲
    If IsDate(MyRange.Value) Then
      MyCount = MyCount + 1
    End If
  Next
  CountDate = MyCount
End Function

最初は完璧と思えたのですが、1点問題がありました。
セルに 38885 と入力した後に表示形式を日付に変更するとカウントしてくれません。
根本的に記述が間違っているのでしょうか?

A 回答 (3件)

2についてですが書式変更時点では確かに計算しませんがそれはユーザー定義関数の仕様で範囲内に入力された時点で正しく計数されますからそ

んなに問題ではないのでは?例えば何かダミー入力するセルを範囲内に設けては?

この回答への補足

つまらない質問にお付き合いいただきましてありがとうございました。
今回の件はもっと単純に考えることにします。
またよろしくお願いします。

補足日時:2006/06/20 22:33
    • good
    • 0
この回答へのお礼

アドバイスありがとうございます。

仰る通りです。
Change Event が発生すれば正しくカウントされますので、無視して差し支えない問題ですね。
表示形式の変更を実行した時点では、Change Event が発生しないのが残念です。

お礼日時:2006/06/18 22:01

>表示形式を日付に変更するとカウントしてくれません


私が追試すると事実と違いました。
私の間違いですかね。
ーーーーー
こういうことですか。
38885は2006/6/17という日付と考えている場合と、数値としての38885 の場合があります。その差は日付書式が設定されているかどうかにあります。
その区別ですが、関数は書式を問題にしませんので、対象外です。
エクセル関数に、ISNUMBER関数は有るが、ISDATE関数は無い。
VBAのNumberFormatLocal も個々具体的な書式のタイプ1つ1つは問題にできても、日付書式類という判別は用意されていないように思います。
VBのIsDate関数も「日付に変換できるかどうかを問題にしている」という(解説書)ことなので、役立たないように思いました。
しかしやってみると、下記例で正しく4と答えが出ました。
内部処理で書式まで問題にしているのでしょうか。
A1:A10に
2
38888
2004/9/4
34
2001/12/9
23
21
1999/3/15

2000/1/12
3345566
ーーー
A2を日付書式に設定し
2
2006/6/20
2004/9/4
34
2001/12/9
23
21
1999/3/15

2000/1/12
3345566
実行すると、5と正しき答えを返すようです。
ーーー
VBAは
Sub test01()
Dim MyCount As Long
Dim MyRange As Range
MyCount = 0
For Each MyRange In Range("A1:A10")
If IsDate(MyRange.Value) Then
MyCount = MyCount + 1
End If
Next
MsgBox MyCount
End Sub
ーーーーー
Sub test02()
Dim MyCount As Long
Dim MyRange As Range
MyCount = 0
For Each MyRange In Range("A1:A10")
MsgBox MyRange.NumberFormatLocal
If MyRange.NumberFormatLocal = "yyyy/m/d" Then
MyCount = MyCount + 1
End If
Next
MsgBox MyCount
End Sub
を実行すると、私の後者のデータで、5となりました。
NumberFormatでなくNumberFormatLocal にするほうがわかりやすいようです。
ただ自分以外が作ったデータやシートだと日付書式が統一されている保証はなく、難しい問題を抱えます。

この回答への補足

つまらない質問にお付き合いいただきましてありがとうございました。
今回の件はもっと単純に考えることにします。
またよろしくお願いします。

補足日時:2006/06/20 22:30
    • good
    • 0
この回答へのお礼

アドバイスありがとうございます。

> 私が追試すると事実と違いました。
> 私の間違いですかね。
私はユーザー定義関数を =CountDate(A1:A10) のように数式に記述してテストしました。
表示形式を変更した直後では Change Event が発生しないようですので、そのため再計算が行われないようです。
Sub プロシージャではそのタイミングのデータを元に計算するので正しくカウントされました。
これはどうしようもないことなのかもしれません。

問題はこの質問より、私が Excel の仕様を理解せずまた明確なカウント仕様を決めていないことと
後からですが認識しました。
例えば、表示形式が文字列で値が"2006/6/28"のセルをカウントするのかしないのか決めていませんでした。
値が文字なのに表示形式が日付のデータをどうするのかも決めていませんでした。
こんな無茶苦茶なデータを入力する人はいないと思いますが・・・
最終的には、見かけが日付なら表示形式に拘わらずカウントするのがベストかな考え直しました。

お礼日時:2006/06/18 22:31

こんにちは。


【質問1】について
=SUMPRODUCT((B2:B6>=DATEVALUE("2006/04/01"))*(LEFT(CELL("format",B2:B6),1)="D"))
とすれば日付の書式B2:B6の範囲で 2006/04/01 以上で、日付の書式が設定されている個数をカウントできると思います。

【質問2】について
コードの中に
Application.Volatile
と記述してはどうでしょう?
表示形式を変更した後にF9を押すと正しい値を返すようになると思います。

この回答への補足

つまらない質問にお付き合いいただきましてありがとうございました。
今回の件はもっと単純に考えることにします。
またよろしくお願いします。

補足日時:2006/06/20 22:32
    • good
    • 0
この回答へのお礼

アドバイスありがとうございます。

CELL 関数と Volatile メソッドを知りませんでした。
とても参考になります。

お礼日時:2006/06/18 22:35

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!