2025/04/25
【ExcelVBA】選択するだけでデータを別の表に移動

【ExcelVBA】選択するだけでデータを別の表に移動

グループなどを管理している表で、隣のグループの表に氏名を移動したいことってありませんか?

今回は、そんな時に便利な右クリックするだけで氏名を移動できる仕組みを実現していきます。
左側の表から右側の表へ、右側の表から左側の表へ移動することができる仕組みになります。

※こちらで開発したファイルは記事の最後にて配布しています。


1. 開発準備

今回は、表の中のセルを右クリックすることで、隣の表にデータを移動するという仕組みを実現してきます。
特定のシートの特定のセルを右クリックすることで何かしら処理を実行するには、該当するシートのシートモジュールを活用します。

シートモジュールは、該当するシートのタブ上で右クリックし、[コードの表示]を選択することで表示することができます。

選択すると、以下のエディタ画面(VBE)が表示されます。
また、該当するシートのシートモジュールが表示された状態になります。
「Option Explicit」は、VBEの設定内容次第では表示されません。「Option Explicit」についての解説はこちらでは省略します。

次に、該当するシートのセル上で右クリックすると同時に処理が実行される特殊なプロシージャ(イベントプロシージャ)を用意する必要があります。
そのためには、シートモジュールの左上のリストから「Worksheet」を選択します。

「Worksheet」を選択すると、自動で「Worksheet_SelectionChange」というプロシージャが表示されます。
このプロシージャは、該当するシート上のいずれかのセルが選択されると同時に処理が実行されるイベントプロシージャになります。

ただ、今回使用するイベントプロシージャは、セル上で右クリックされると同時に処理が実行されるものになります。
そのため、右上のリストから「BeforeRightClick」を選択します。

表示された「Worksheet_BeforeRightClick」というプロシージャを活用します。
「Worksheet_SelectionChange」というプロシージャに関しては削除して問題ないです。


2. コードの記述

以下のコードを記述します。

Private Sub Worksheet_BeforeRightClick(ByVal Target As Range, Cancel As Boolean)
    
    If Target.CountLarge = 1 And _
        Target.Row >= 3 Then
        
        Dim lRow As Long
        If Target.Column = 2 Then
            Cancel = True
            lRow = Cells(Rows.Count, "C").End(xlUp).Row
            Cells(lRow + 1, "C").Value = Target.Value
            Target.Delete xlUp
        ElseIf Target.Column = 3 Then
            Cancel = True
            lRow = Cells(Rows.Count, "B").End(xlUp).Row
            Cells(lRow + 1, "B").Value = Target.Value
            Target.Delete xlUp
        End If
        
    End If
    
End Sub

では、コードについて解説していきます。

Private Sub Worksheet_BeforeRightClick(ByVal Target As Range, Cancel As Boolean)
    
    If Target.CountLarge = 1 And _
        Target.Row >= 3 Then
        
        '省略
        
    End If
    
End Sub

「Worksheet_BeforeRightClick」というプロシージャの引数の「Target」に、右クリックされたセルの情報が渡されるため、そのセルの情報から、表の対象の範囲内が右クリックされたかどうかを確認しています。
こちらでは、「右クリックされたセルが単体(複数範囲を選択した上での右クリックでない)で3行目以上のセル」と、まずは対象の表のデータ行が右クリックされたかどうかを確認しています。

この条件を満たした場合に関してのみ、Ifの中の処理を実行します。

        Dim lRow As Long
        If Target.Column = 2 Then
            '省略
        ElseIf Target.Column = 3 Then
            '省略
        End If

lRowという変数は、移動先の表の最終行の行番号を格納する用の変数になります。
こちらは後で使用します。

その次のIfで、右クリックされたセルが2列目(B列)なのか3列目(C列)なのかによって、処理を分岐しています。

            Cancel = True
            lRow = Cells(Rows.Count, "C").End(xlUp).Row
            Cells(lRow + 1, "C").Value = Target.Value
            Target.Delete xlUp

右クリックされたセルが2列目(B列)の場合は、「Cancel = True」で右クリック時のメニューが表示されないようにし、lRowに移動先の表(C列)の最終行の行番号を格納しています。
行番号は、C列の一番下のセルからCtrlキーとカーソルキーの上を押して止まった位置のセルの行番号を最終行の行番号として取得しています。
その次に、その取得した行番号の1つ下のセルに、右クリックされたセルの値を格納し、右クリックされたセルを削除して上に詰めています。

            Cancel = True
            lRow = Cells(Rows.Count, "B").End(xlUp).Row
            Cells(lRow + 1, "B").Value = Target.Value
            Target.Delete xlUp

右クリックされたセルが3列目(C列)の場合は、先ほどのB列とC列を入れ替えた処理を行っています。


3. 完成

以上の内容で実現できます。
移動したい氏名が入力されているセルの上で、右クリックすることで、その氏名を隣の表に移動することができます。

▼サンプルファイル▼

2025/04/22
【Excel】自動でグループ分け!FILTER関数×TEXTJOIN関数

【Excel】自動でグループ分け!FILTER関数×TEXTJOIN関数

以下の表は、氏名ごとに曜日を割り当てたものになります。

今回は、こちらの表から曜日ごとで氏名をカンマ区切りにして抽出する方法について紹介していきます。


FILTER関数とTEXTJOIN関数

カンマ区切りで並べて抽出するには、FILTER関数とTEXTJOIN関数を活用します。

FILTER関数では、以下のように条件を満たしたデータのみを抽出することができます。

=FILTER(D:D,E:E="月","")

TEXTJOIN関数では、以下のように指定した複数の値を指定した区切り文字で繋げて表示することができます。

=TEXTJOIN(",",TRUE,D3:D7)

そのため、この2つ関数を組み合わせて、対象のデータの抽出と抽出データの結合を1つ数式で行うことができます。


曜日ごとで氏名をカンマ区切りにして抽出

こちらでは、以下のB列の表に曜日ごとで抽出していきます。

まずは、「月」から抽出していきます。
「月」を抽出する数式は、以下になります。

=TEXTJOIN(",",TRUE,FILTER(D:D,E:E=B2,""))
// FILTER関数で「月」と一致する氏名を抽出し、TEXTJOIN関数でカンマ区切りにして結合

このように、1つの数式で抽出することができます。
他の曜日に関しては、数式を入力したセルをコピーして貼り付けるだけで抽出することができます。

それぞれのセルに貼り付けられる数式は、以下のように相対参照で反映されます。

火:=TEXTJOIN(",",TRUE,FILTER(D:D,E:E=B4,""))
水:=TEXTJOIN(",",TRUE,FILTER(D:D,E:E=B6,""))
木:=TEXTJOIN(",",TRUE,FILTER(D:D,E:E=B8,""))
金:=TEXTJOIN(",",TRUE,FILTER(D:D,E:E=B10,""))

まとめ

FILTER関数とTEXTJOIN関数の組み合わせは、単に曜日ごとの担当者を抽出するだけでなく、様々な条件に基づいたデータの抽出と結合を自動化できる、非常に汎用性の高いテクニックです。

これらの関数を使いこなすことで、
・データ分析の効率化
・レポート作成の自動化
・日々のルーチンワークの削減

などといった、Excelを使った業務の効率を向上させることができます。

2025/04/18
【ExcelVBA】省略した項目を自動で入力

【ExcelVBA】省略した項目を自動で入力

以下のように、所属(学年とクラス)と氏名を入力する表で、同じ所属の名前を複数件登録することがあるかと思います。

その際に、毎回同じ所属(学年とクラス)を入力するのは面倒ですし、コピーするのも地味に面倒です。
そのため今回は、所属(学年とクラス)を省略した場合は、1つ前の所属を自動で入力する仕組みの開発方法について紹介していきます。
色んな表で活用できる便利な機能になります。

※こちらで開発したファイルは記事の最後にて配布しています。


1. 開発準備

今回は、以下の表の「氏名」の項目に値が入力された時に、「学年」の項目が空欄だった場合は1つ前の「学年」を入力、「クラス」の項目が空欄だった場合は1つ前の「クラス」を入力するという仕組みを実現していきます。

そのように、特定のシートで特定のセルが編集された時に処理を自動で実行するには、「シートモジュール」の「イベントプロシージャ」を活用します。
シートモジュールは、該当するシートのタブ上で右クリックし、[コードの表示]を選択することで表示することができます。

選択すると、以下のエディタ画面(VBE)が表示されます。
また、該当するシートのシートモジュールが表示された状態になります。
「Option Explicit」は、VBEの設定内容次第では表示されません。「Option Explicit」についての解説はこちらでは省略します。

次に、該当するシートのセルに値を入力すると同時に処理が実行される特殊なプロシージャ(イベントプロシージャ)を用意する必要があります。
そのためには、シートモジュールの左上のリストから「Worksheet」を選択します。

「Worksheet」を選択すると、自動で「Worksheet_SelectionChange」というプロシージャが表示されます。
このプロシージャは、該当するシート上のいずれかのセルが選択されると同時に処理が実行されるイベントプロシージャになります。

ただ、今回使用するイベントプロシージャは、セルに値を入力すると同時に処理が実行されるものになります。
そのため、右上のリストから「Change」を選択します。

表示された「Worksheet_Change」というプロシージャを活用します。
「Worksheet_SelectionChange」というプロシージャに関しては削除して問題ないです。


2. コードの記述

以下のコードを記述します。

Private Sub Worksheet_Change(ByVal Target As Range)
    
    Dim r As Long: r = Target.Row
    Dim c As Long: c = Target.Column
    
    If r >= 3 And c = 4 Then
        If Cells(r, "B").Value = "" Then
            Cells(r, "B").Value = _
                Cells(r - 1, "B").Value
        End If
        If Cells(r, "C").Value = "" Then
            Cells(r, "C").Value = _
                Cells(r - 1, "C").Value
        End If
    End If

End Sub

では、コードについて解説していきます。

Private Sub Worksheet_Change(ByVal Target As Range)
    
    Dim r As Long: r = Target.Row
    Dim c As Long: c = Target.Column
    
    If r >= 3 And c = 4 Then
        
        '省略
        
    End If

End Sub

「Worksheet_Change」というプロシージャの引数の「Target」に、編集されたセルの情報が渡されるため、そのセルの情報から、表の対象のセルが編集されたかどうかを確認しています。
こちらでは、Targetの行番号と列番号を変数「r」と「c」に格納し、「r」が3以上、尚且つ、「c」が4の時、要するに「氏名」の項目が編集されたかどうかを確認しています。

この条件を満たした場合に、Ifの中の処理を実行します。

        If Cells(r, "B").Value = "" Then
            Cells(r, "B").Value = _
                Cells(r - 1, "B").Value
        End If
        If Cells(r, "C").Value = "" Then
            Cells(r, "C").Value = _
                Cells(r - 1, "C").Value
        End If

こちらでは、学年の項目(r行目のB列)が空欄なのか、クラスの項目(r行目のC列)が空欄なのかを確認しています。
学年の項目(r行目のB列)が空欄の場合は、その項目の1つ前の値(r-1行目のB列)を入力しています。
クラスの項目(r行目のC列)に関しても同様に、空欄の場合は、その項目の1つ前の値(r-1行目のC列)を入力しています。


3. 完成

以上の内容で実現できます。
「氏名」の項目に値が入力された時に、「学年」の項目が空欄だった場合は1つ前の「学年」が入力され、「クラス」の項目が空欄だった場合は1つ前の「クラス」が入力されます。

▼サンプルファイル▼

2025/04/15
【Excel】同じ日付が一定間隔で続く予定表を効率的に作成

【Excel】同じ日付が一定間隔で続く予定表を効率的に作成

以下のように、同じ日程が一定間隔で続く予定表を作成したことはありませんか。

このような表を手作業で入力していくのは大変ですし、ミスも起こりやすくなります。
ということで今回は、同じ日付が一定間隔で続く予定表を効率的に作成する方法について紹介します。

同じ日付が一定間隔で続く連続した日付を入力

直接的に「一定間隔で同じ日付を繰り返す」という機能は存在しませんが、オートフィルの使い方を少し工夫することで、実現することができます。

(例)3行間隔で連続した日付を入力する場合

1. 開始日を必要な回数入力する

2. 次の行に、先頭行の日付に1を加えた日付を表示する数式を入力する

3. 入力した数式を必要な行数分コピーする(オートフィル)

これだけです。
数式の参照先が相対的に変化するため、日付を一定間隔で繰り返して入力することができます。


同じ組み合わせの値を繰り返して入力

担当の項目に「A→B→C」などと繰り返した値を入力する場合にも、オートフィルが活用できます。

(例)「A→B→C」を繰り返して入力する場合

1. 繰り返す1周分の値を入力する

2. 入力したセルを選択し、必要な行数分コピーする(オートフィル)

これだけです。


まとめ

オートフィルの機能を少し工夫して活用することで、一定間隔で続く予定表を作成することができました。
表に法則性のあるデータを入力する際は、オートフィルの機能を使って効率的に入力できないかどうかを検討してみると良いです。

2025/04/11
【Excel】年月を変更するだけで万年使えるカレンダー

【Excel】年月を変更するだけで万年使えるカレンダー

以下のように、年月の項目を指定するだけで、自動でその月のカレンダーに切り替わるシートの作成方法について解説していきます。

※こちらのファイルは、記事の最後にて配布しています。


1. 指定した年月の1日の日付を表示する

まず、DATE関数を活用して、指定した年月の1日の日付を表示します。

=DATE(B2,B3,1)

これで、B2とB3に入力した年月の1日の日付が表示されます。


2. 2日以降の日付を表示する

2日以降の日付は、前の日付に1日を加えることで表示できます。

=A6+1

1つ数式を入力したら、下へ28日が表示されるまでコピーします。


3. 29日以降の日付を表示する

月によっては29日以降が不要になるため、29日以降に関しては、対象年月の月末日を超えていないかどうかを確認する必要があります。

そのためには、対象年月の月末日を取得する必要があります。
年月から月末日を取得するには、DATE関数で「翌月1日の1日前」と指定します。

=DATE(B2,B3+1,0)
// 1日の1日前なので、日を「0」と指定する

取得した月末日と前の日付(1つ上のセル)と比較し、月末日の方が大きい場合に、前の日付に1日を加えた日付を表示させます。
条件を確認し表示の有無を切り替える場合は、IF関数を活用します。

=IF(DATE(B2,B3+1,0)>A33,A33+1,"")

こちらの場合は、2025年2月の日付を表示しているため、28日の次の日付が表示されないことが確認できます。

こちらの数式を残り2行分(31日分)入力する必要があります。
そのため、数式の年月を参照しているセルに「$」を加えて固定してからコピーします。

=IF(DATE($B$2,$B$3+1,0)>A33,A33+1,"")

上記の画像のセルA35とA36が空になる理由は、IF関数の条件式(論理式)で空と比較しているためです。

文字列(数式により表示された空の文字列「””」)と数値を比較した場合、文字列の方が大きいと判断されるため、IF関数の条件を満たさず空の文字列「””」が表示されます。
※何も入力されていないセルの場合は「0」として扱われるため、挙動が異なります。


4. 曜日を表示する

日付から曜日を取得するには、TEXT関数を活用します。
以下のように、TEXT関数を活用して日付に対応する曜日を表示します。

=TEXT(A6,"aaa")
// 「aaa」は曜日を表示する書式記号

1つ数式を入力したら、最終行までコピーします。

日付の項目が空の文字列「””」の行に関しては、空の文字列「””」が表示されます。
※何も入力されていないセルの場合は「0」として扱われるため、挙動が異なります。


5. 完成

これで、指定した年月に応じてカレンダーが自動的に切り替わる仕組みが完成しました。
関数を組み合わせることで、ある程度は自動化することができます。
今回は、DATE関数IF関数TEXT関数の3つの関数を活用しました。
これらの関数は、よく使われるため覚えておくと良いです。

▼サンプルファイル▼

2025/04/08
【Excel】シートを完全に非表示にする

【Excel】シートを完全に非表示にする

特定のシートを隠したい場合、通常の「非表示」設定では再表示から簡単に表示されてしまいます。

再表示させない目的で、ブックを保護するという方法もありますが、ブックを保護してしまうと、「シートが移動できない、追加できない」などと扱いづらくなってしまいます。

そこで、本記事では、再表示では表示できない「シートを完全に非表示にする」方法について解説していきます。

ExcelVBAレベル確認

「通常の非表示」と「完全非表示」の違い

Excelには、以下の2種類の非表示設定があることはご存じでしょうか。

1.通常の非表示(再表示で簡単に戻せる)
2.完全非表示(再表示からは戻せない)

恐らく、2つ目の「完全非表示」の設定方法については知らない方がほとんどかと思います。
2つ目の方法を活用することで、ブックを保護しなくてもシートを隠し、誤って表示されるリスクを防ぐことができます。
途中計算用のシートなど、あまり触ってほしくないシートに活用すると良いです。

ただ注意点として、しばらく操作をしていないと、設定した本人すらシートの存在を忘れてしまう可能性があります。
後継ぎなどのことも考慮した上で、非表示にした際の手順書を残しておくと良いです。


シートを「完全非表示」にする方法

シートを完全に非表示にするためには、「VBE(Visual Basic Editor)」を活用します。
通常、VBEはマクロを開発する際に活用する画面ですが、今回はマクロの開発は行いません。
そのため、マクロ有効ブックにする必要もないです。

① VBEを開く

「Alt」キーを押しながら「F11」キーを押すことで、VBEの画面を開くことができます。
[開発]タブが表示されている場合は、[開発]タブの中の[Visual Basic]を選択することでも開くことができます。

② 「プロジェクトエクスプローラー」と「プロパティウィンドウ」を表示する

VBEの画面に「プロジェクトエクスプローラー」と「プロパティウィンドウ」が表示されていない場合は、[表示]メニューから表示します。

③ 「完全非表示」にする対象のシートのプロパティを表示する

「完全非表示」にする対象のシートを選択するか、「プロジェクトエクスプローラー」から対象のシートの項目を選択します。
選択すると、「プロパティウィンドウ」に対象のシートのプロパティが表示されます。
対象のシートのプロパティかどうかは「Name」の項目で確認することができます。
こちらでは「休日一覧」シートを選択しています。

④ 「完全非表示」を設定する

対象のシートの「Visible」プロパティを「2 – xlSheetVeryHidden」にします。

以上です。
これで対象のシートを完全に非表示にすることができます。

この方法で非表示にした場合は、「再表示」からは表示することができません。

ただ、シート自体は存在しているため、数式などで参照することはできます。


シートを再表示する方法

「完全非表示」にしたシートを再表示する際は、VBEのプロパティウィンドウから設定します。
再表示する際は、「プロジェクトエクスプローラー」から対象のシートの項目を選択し、対象のシートの「Visible」プロパティを「-1 – xlSheetVisible」に戻します。

これだけで、非表示にしたシートを表示することができます。


まとめ

シートを完全に非表示にすると、誤って表示されるリスクを防げます。
完全に非表示にしても、VBAや数式で参照することは可能です。
ぜひ試してみてください。

2025/04/04
【ExcelVBA】シートの「表示・非表示」を瞬時に切り替える

【ExcelVBA】シートの「表示・非表示」を瞬時に切り替える

以下のようにシートの数が増えすぎると、シートの移動が面倒になりますよね。

シートの一覧を表示して対象のシートを選択するということもできますが、毎回一覧を表示するというのも面倒になります。

そのような時は、不要なシートを非表示にすると思いますが、このシートを非表示にしたり再表示にしたりする作業も地味に面倒ですよね。

ということで今回は、シート名の一覧シートを用意し、そのシートで対象のシート名をダブルクリックするだけでシートの「表示・非表示」を切り替えることができる仕組みを実現していきます。

※こちらで開発したファイルは記事の最後にて配布しています。

ExcelVBAレベル確認

1. 開発準備

まず初めに、シート名の一覧シートを用意します。
こちらでは、以下のようなシート名と表示の有無(●なら表示)を管理した表を、シートを追加して用意しています。

次は、用意したシートの「表示」の項目をダブルクリックすることで、対象シートの「表示・非表示」を切り替える仕組みを実現していきます。

「特定のセルをダブルクリックすると同時に、何かしら処理を実行する」という仕組みは、該当するシートモジュールイベントプロシージャを活用することで実現できます。

シートモジュールは、該当するシートのタブ上で右クリックし、[コードの表示]を選択することで表示することができます。

選択すると、以下のエディタ画面(VBE)が表示されます。
また、該当するシートのシートモジュールが表示された状態になります。
「Option Explicit」は、VBEの設定内容次第では表示されません。「Option Explicit」についての解説はこちらでは省略します。

次に、該当するシートのセルをダブルクリックすると同時に処理が実行される特殊なプロシージャ(イベントプロシージャ)を用意する必要があります。
そのためには、シートモジュールの左上のリストから「Worksheet」を選択します。

「Worksheet」を選択すると、自動で「Worksheet_SelectionChange」というプロシージャが表示されます。
このプロシージャは、該当するシート上のいずれかのセルが選択されると同時に処理が実行されるイベントプロシージャになります。

ただ、今回使用するイベントプロシージャは、セルがダブルクリックされると同時に処理が実行されるものになります。
そのため、右上のリストから「BeforeDoubleClick」を選択します。

表示された「Worksheet_BeforeDoubleClick」というプロシージャを活用します。
「Worksheet_SelectionChange」というプロシージャに関しては削除して問題ないです。

2. コードの記述

以下のコードを記述します。

Private Sub Worksheet_BeforeDoubleClick(ByVal Target As Range, Cancel As Boolean)
    
    If Target.Row >= 3 And _
        Target.Column = 3 Then
        
        Cancel = True
        
        Dim wsName As String
        wsName = Cells(Target.Row, "B").Value
        
        On Error Resume Next
        If Target.Value = "" Then
            Target.Value = "●"
            Worksheets(wsName).Visible = True
        Else
            Target.ClearContents
            Worksheets(wsName).Visible = False
        End If
        
    End If
    
End Sub

では、コードについて解説していきます。

Private Sub Worksheet_BeforeDoubleClick(ByVal Target As Range, Cancel As Boolean)
    
    If Target.Row >= 3 And _
        Target.Column = 3 Then
        
        '省略
        
    End If
    
End Sub

「Worksheet_BeforeDoubleClick」というプロシージャの引数の「Target」に、ダブルクリックされたセルの情報が渡されるため、そのセルの情報から、表の対象の範囲内がダブルクリックされたかどうかを確認しています。
こちらでは、「3行目以上、尚且つ、3列目のセル」と「表示」のセルの範囲内がダブルクリックされたかどうかを確認しています。

この条件を満たした場合に関してのみ、Ifの中の処理を実行します。

        Cancel = True
        
        Dim wsName As String
        wsName = Cells(Target.Row, "B").Value

セルをダブルクリックすると、通常、セルが編集モードになるのですが、引数の「Cancel」をTrueにすることで、編集モードにならなくなります。
その次に、ダブルクリックされた行と同じ行のB列の値(シート名)を変数(wsName)に格納しています。

        On Error Resume Next
        If Target.Value = "" Then
            Target.Value = "●"
            Worksheets(wsName).Visible = True
        Else
            Target.ClearContents
            Worksheets(wsName).Visible = False
        End If

次に、ダブルクリックされたセルの値の有無を確認しています。
値が空の場合は、ダブルクリックされたセルに「●」を入力し、先ほど取得したシート名(wsName)のシートを表示しています。
値が空でない場合は、ダブルクリックされたセルの値をクリアし、先ほど取得したシート名(wsName)のシートを非表示にしています。

先頭の「On Error Resume Next」はエラー対策です。
変数(wsName)に格納されているシート名のシートが存在しない場合に、エラーにならないように、エラーの場合は無視をして続行するという記述になります。

3. 完成

以上の内容で実現できます。
シートの「表示・非表示」を切り替えたい対象のシート名が入力されている行のC列のセルをダブルクリックすることで、そのシートの「表示・非表示」を切り替えることができます。

▼サンプルファイル▼

2025/04/01
【Excel】VLOOKUP関数で複数の表から検索

【Excel】VLOOKUP関数で複数の表から検索

通常、VLOOKUP関数では、1つの表から検索して値を抽出します。
しかし、以下の表のように、複数に分かれた表で管理されていることもあるかと思います。

今回は、VLOOKUP関数を活用して、複数に分かれた全ての表から検索して値を抽出する方法について2通りで解説していきます。


方法1

VLOOKUP関数を活用して、1つの表から検索して値を抽出する場合の数式は以下のようになります。

=VLOOKUP(B3,B6:C20,2,FALSE)

ただ、この数式のままですと、対象が見つからない場合にエラーになってしまいますよね。

そのため、まずはエラー対策としてIFERROR関数を組み合わせます。
IFERROR関数の使い方は、以下になります。

=IFERROR(値, エラーの場合の値)
//指定した[値]がエラーの場合は、指定した[エラーの場合の値]を返す

実際に組み合わせると、以下のようになります。

=IFERROR(VLOOKUP(B3,B6:C20,2,FALSE),"")
// エラーの場合は何も表示しない("")

これで、エラーの場合は何も表示されなくなりました。

後は、もう片方の表から抽出する数式を、以下のように「&」で文字結合するだけで、複数の表から検索して値を抽出することができます。

=IFERROR(VLOOKUP(B3,B6:C20,2,FALSE),"")&IFERROR(VLOOKUP(B3,E6:F20,2,FALSE),"")

複数の表に重複した検索値が含まれていない場合は、いずれか1つのVLOOKUP関数の数式でしか値が抽出されず、他のVLOOKUP関数の数式ではエラーとなり、IFERROR関数で空が返されます。
そのため、上記のように、1つの値のみが抽出されます。


方法2

次の方法は、VSTACK関数を活用する方法になります。
VSTACK関数を活用することで、複数の表を縦に結合することができるため、離れている複数の表を縦に結合した表をVLOOKUP関数の範囲に指定することができます。
VSTACK関数は、現時点では365のバージョンでないと活用することができません。
VSTACK関数の使い方は、以下になります。

=VSTACK(範囲1,範囲2,範囲3,…)
// 指定した[範囲]を縦に結合して返す

VLOOKUP関数の範囲を指定する際に、VSTACK関数を組み合わせて指定することで、複数の表を縦に結合した範囲から検索して値を抽出することができます。
実際に組み合わせた数式が以下になります。

=VLOOKUP(B3,VSTACK(B6:C20,E6:F20),2,FALSE)

上記の数式では、IFERROR関数を使用していないため、対象が見つからない時にエラーになってしまいます。

必要に応じて、以下のようにIFERROR関数を組み合わせると良いです。

=IFERROR(VLOOKUP(B3,VSTACK(B6:C20,E6:F20),2,FALSE),"")
2025/03/28
【ExcelVBA】完了タスクを非表示にして着手中タスクを上位表示する

【ExcelVBA】完了タスクを非表示にして着手中タスクを上位表示する

以下のようなタスク管理表で、完了したタスクを非表示にして、着手中のタスクを上位に表示するという作業があるとします。
この作業をタスクの進捗を更新する度、手動で行うのは大変ですよね。

そこで今回は、「着手日」または「完了日」を入力すると同時に、これらの操作を自動で行う仕組みの実現方法を解説していきます。
※こちらで開発したファイルは記事の最後にて配布しています。


1. 開発準備

今回は、以下の表の「着手日」もしくは「完了日」の項目に値が入力されると同時に処理を実行します。

そのように、特定のシートで特定のセルが編集された時に処理を自動で実行するには、「シートモジュール」の「イベントプロシージャ」を活用します。
シートモジュールは、該当するシートのタブ上で右クリックし、[コードの表示]を選択することで表示することができます。

選択すると、以下のエディタ画面(VBE)が表示されます。
また、該当するシートのシートモジュールが表示された状態になります。
「Option Explicit」は、VBEの設定内容次第では表示されません。「Option Explicit」についての解説はこちらでは省略します。

次に、該当するシートのセルに値を入力すると同時に処理が実行される特殊なプロシージャ(イベントプロシージャ)を用意する必要があります。
そのためには、シートモジュールの左上のリストから「Worksheet」を選択します。

「Worksheet」を選択すると、自動で「Worksheet_SelectionChange」というプロシージャが表示されます。
このプロシージャは、該当するシート上のいずれかのセルが選択されると同時に処理が実行されるイベントプロシージャになります。

ただ、今回使用するイベントプロシージャは、セルに値を入力すると同時に処理が実行されるものになります。
そのため、右上のリストから「Change」を選択します。

表示された「Worksheet_Change」というプロシージャを活用します。
「Worksheet_SelectionChange」というプロシージャに関しては削除して問題ないです。


2. コードの記述

以下のコードを記述します。

Private Sub Worksheet_Change(ByVal Target As Range)
    
    If Target.Row >= 3 And _
       Target.Column >= 4 And _
       Target.Column <= 5 Then
        
        Range("B2").AutoFilter _
            Field:=4, _
            Criteria1:=""
        
        Range("B2").Sort _
            Key1:=Range("D2"), _
            Order1:=xlAscending, _
            Header:=xlYes
        
    End If
    
End Sub

では、コードについて解説していきます。

Private Sub Worksheet_Change(ByVal Target As Range)
    
    If Target.Row >= 3 And _
       Target.Column >= 4 And _
       Target.Column <= 5 Then
        
        '省略
        
    End If
    
End Sub

「Worksheet_Change」というプロシージャの引数の「Target」に、編集されたセルの情報が渡されるため、そのセルの情報から、表の対象のセルが編集されたかどうかを確認しています。
こちらでは、Targetの行番号が3以上、尚且つ、列番号が4以上、5以下の時、要するに「着手日」もしくは「完了日」の項目が編集されたかどうかを判定しています。

この条件を満たした場合に、Ifの中の処理を実行します。

        Range("B2").AutoFilter _
            Field:=4, _
            Criteria1:=""

まずは、絞り込みです。
セルB2を含む表の先頭から4列目の項目「完了日」に対し、空白のセルで絞り込みをしています。

        Range("B2").Sort _
            Key1:=Range("D2"), _
            Order1:=xlAscending, _
            Header:=xlYes

次に、並べ替えです。
セルB2を含む表を、セルD2の列の項目「着手日」を基準に昇順(xlAscending)にしています。
表には見出し(項目名)が含まれるため、「Header:=xlYes」と指定しています。

ExcelVBAレベル確認

3. 完成

以上の内容で実現できます。

「完了日」に値を入力すると同時に、そのタスクが非表示になります。

また、「着手日」を入力すると同時に、「着手日」を基準に昇順で並べ替えられます。

▼サンプルファイル▼

2025/03/25
【Excel】スクロールバーを活用して行の色付け

【Excel】スクロールバーを活用して行の色付け

以下のように、スクロールバーを操作するだけで、表の行の色付け位置を変更することができる仕組みの実現方法について解説していきます。


1. 条件付き書式で特定の行を色付け

今回は、以下の表に対して行の色付けを行います。

まずは、色付けの対象となる行の行番号を表の上のセルに入力します。
※セルに入力した値は最終的にスクロールバーで見えなくなります。

こちらでは、セルB2に「5」と入力しています。

次に、表の範囲の先ほど指定した行番号の行を自動で色付けする設定を『条件付き書式』にて行います。

まずは、表の要素全体を選択し、[ホーム]タブの中の[条件付き書式]から[新しいルール]を選択します。

表示された条件付き書式の設定画面で、[ルールの種類]を[数式を指定して、書式設定するセルを決定]にし、以下の条件式を入力します。

=ROW()=$B$2
// 対象のセルの行番号とセルB2の値が同じ場合
// 「B2」は「$B$2」と絶対参照にする

次に、[書式]から好みの書式を設定します。
こちらでは、[塗りつぶし]タブから黄色を指定しています。

上記の手順で確定することによって、以下のように指定した行が自動で色付けされます。


2. スクロールバーを使って色付けする行を変更

続いて、スクロールバーを作成します。

まずは、[開発]タブの中の[挿入]の[フォームコントロール]から[スクロールバー]を選択し、表の上に作成します。
※Altキーを押しながら作成すると、セルの幅に自動で調整されます。

次に、作成したスクロールバー上で右クリックし、[コントロールの書式設定]を選択します。

表示された書式設定の画面で必要な設定を行います。
こちらでは、以下のように設定しています。

現在値:5
最小値:4(表が4行目から用意されているため)
最大値:23(表が23行目まで用意されているため)
変化の増分:1(スクロールバーの縁を押した時に動かす量)
スクロールバー シャフトの増分:5(スクロールバーの中の隙間を押した時に動かす量)
リンクするセル:B2(行番号を入力したセルのアドレス)

以上の設定で完成です。
以下のように、スクロールバーを操作するだけで、表の行の色付け位置を変更することができます。

2025/03/21
【Excel】6桁の年月を簡単に入力

【Excel】6桁の年月を簡単に入力

「202501、202502…」のように6桁の年月を並べたい時に、通常のドラッグ操作ではうまくいかないことがあります。

ということで、こちらでは6桁の年月を簡単に入力する方法について解説していきます。


数式の入力

まずは、入力したい先頭の6桁の年月を数式で求めていきます。
その際に、ROW関数DATE関数TEXT関数を活用します。
それぞれの関数の使い方は、以下になります。

=ROW(参照)
// 参照したセルの行番号を返す
=DATE(年, 月, 日)
// 指定した年月日から該当する日付を返す
// 指定した月や日が存在しない数値の場合は桁上げ桁下げした日付を返す
=TEXT(値, 表示形式)
// 指定した値に対し、指定した表示形式を適用した文字列を返す

まずはROW関数とDATE関数を組み合わせて、先頭の年月の1日を求めていきます。
※1日でなくても、全ての年月に存在する日付なら問題ございません。

日付に関しては、下の行へコピーすることで、1月、2月と翌月の日付にする必要があるため、月はROW関数でセルの行番号を活用して求めます。
例えば、2025年1月から入力したい場合は、以下のような数式になります。

=DATE(2025,ROW(A1),1)

次は、この数式にTEXT関数を組み合わせて年月のみを表示させます。
年月のみを6桁で表示する表示形式は「yyyymm」になるため、以下のような数式になります。

=TEXT(DATE(2025,ROW(A1),1),"yyyymm")

以上の手順で、年月のみを表示することができます。

ただ、この状態のままですと、表示された6桁の年月は文字列として扱われます。
数値として扱いたい場合は、更にVALUE関数で囲むことで数値に変換できます。
VALUE関数で囲んだ数式は以下になります。

=VALUE(TEXT(DATE(2025,ROW(A1),1),"yyyymm"))

VALUE関数で囲んだ結果、以下のような変な日付が表示される場合は、表示形式を「標準」に戻すとよいです。

ExcelVBAレベル確認

数式のコピー

先頭の年月を求める数式の入力ができましたら、後は必要な行までドラッグしてコピーするだけです。

これだけで、6桁の年月を必要な数分入力することができます。

まとめ

この方法を使えば、6桁の年月を簡単に連続で入力できます。

1. 以下の数式を入力する
※数値として扱いたい場合はVALUE関数で囲む

=TEXT(DATE(年, ROW(A1), 1), "yyyymm")
// 年:開始の年を指定
// A1:開始の月と同じ行番号のセルを指定

2. 必要な行までドラッグしてコピーする

横向きに入力したい場合は、ROW関数ではなくCOLUMN関数を活用します。
COLUMN関数の使い方は、以下になります。

=COLUMN(参照)
// 参照したセルの列番号を返す

実際にCOLUMN関数を活用すると、以下のような数式になります。

=VALUE(TEXT(DATE(2025,COLUMN(A1),1),"yyyymm"))
2025/03/18
【Excel】シートの追加と削除を一瞬で行うショートカット

【Excel】シートの追加と削除を一瞬で行うショートカット

作業中に簡単なメモや計算をするために、一時的にシートを追加することがあります。
しかし、不要になったシートを削除する際に、シートタブの上で右クリックして削除するのは少し面倒です。

そこで今回は、シートの追加と削除を一瞬で行うショートカットを紹介します。


シートの追加

シートを追加するには、以下のショートカットを使用します。

「Shift + F11」もしくは「Alt + Shift + F1」
他にも、「Alt → H → I → S」「Alt → I → W」でも追加できます。

「Alt → H → I → S」は以下のように[ホーム]タブから順にキーで指定しています。

「Alt → I → W」は古いバージョンのショートカットですが、最新のバージョンでも使うことができます。
※Altの後にIを押すと、「Officeのアクセスキー」の画面が表示されます。

ExcelVBAレベル確認

シートの削除

不要になったシートを削除するには、以下のショートカットを使います。

「Alt → H → D → S」もしくは「Alt → E → L」

「Alt → H → D → S」は以下のように[ホーム]タブから順にキーで指定しています。

「Alt → E → L」は古いバージョンのショートカットですが、最新のバージョンでも使うことができます。
※Altの後にEを押すと、「Officeのアクセスキー」の画面が表示されます。

シートに情報が含まれている場合は、上記のショートカットを入力した後に、以下のような画面が表示されます。
その際は、Enterを押すことで「削除」が選択され、シートを削除することができます。

複数シートを選択している状態で上記のショートカットを入力することで、複数シートを同時に削除することもできます。