0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

📊連載第27回!初心者のためのExcel VBA入門:相対パスで親フォルダアクセス!🗂️ FileSystemObjectでエラーに強いコード作り💪

Last updated at Posted at 2025-07-30

Excel VBAにおける親フォルダパス取得の実装テクニック

私はVBAの活用経験を通じて得た知識を整理し、共有する目的で記事を作成しているプログラミング歴1年半になるエンジニアです。前回は、再帰処理を活用したファイル・フォルダ移動について詳しく説明しました。今回は、Excelファイルが保存されている場所から親フォルダのパス(一つ上の階層のフォルダ)を自動的に取得する実用的なテクニックについて解説します。

目次

はじめに

Excelマクロを作成する際、現在のワークブックが保存されているフォルダの一つ上の階層(親フォルダ)にアクセスしたいケースがよくあります。例えば、設定ファイルを読み込んだり、処理結果を特定のフォルダに保存したり、テンプレートファイルを参照したりする場合です。

ハードコード(直接パスを記述)してフォルダパスを指定することが多く、ファイルを別の場所に移動すると動作しなくなるという問題がありました。また、異なるユーザー環境では同じパス構造が存在しないことも多く、ポータビリティ(異なる環境での動作性)に課題がありました。

本記事で紹介するテクニックを使用することで、Excelファイルがどの場所に保存されていても、自動的に親フォルダのパスを取得し、環境に依存しない柔軟なマクロを作成することができます。これにより、ファイルの配布や移動時にもマクロの修正が不要となり、メンテナンス性が大幅に向上します。

親フォルダパス取得の基本概念

フォルダ階層の理解

Windowsのフォルダ構造は、木構造(ツリー)のように階層化されています。

C:\
├── Users\
│   ├── UserName\
│   │   ├── Documents\
│   │   │   ├── Excelファイル\      ← 現在のワークブックの場所
│   │   │   │   └── sample.xlsx
│   │   │   ├── 設定フォルダ\
│   │   │   └── テンプレート\
│   │   └── Desktop\
│   └── Public\
└── Program Files\

この例では、sample.xlsxC:\Users\UserName\Documents\Excelファイル\に保存されている場合、親フォルダC:\Users\UserName\Documents\となります。

パス(Path)とは

パスは、コンピューター内のファイルやフォルダの場所を示す文字列です。フォルダの区切りには「\」(バックスラッシュ)が使用されます。パスを理解することで、ファイル操作の幅が大きく広がります。

相対パス記法の活用

親フォルダを表現する最も簡単な方法は、相対パス記法の「..」(ドットドット)を使用することです。

記法 意味
. 現在のフォルダ
.. 親フォルダ(一つ上の階層)
..\.. 親の親フォルダ(二つ上の階層)

この記法により、現在のファイルの場所から相対的に親フォルダを指定できます。

ThisWorkbook.Pathを活用した基本実装

基本的な親フォルダパス取得

VBAでは、ThisWorkbook.Pathプロパティを使用して現在のワークブックが保存されているフォルダのパスを取得できます。

' ワークブックが保存されているフォルダと親フォルダのパスを表示
Sub GetParentFolderPath()

    ' 現在のワークブックのフォルダパスを取得
    Dim currentPath As String
    currentPath = ThisWorkbook.Path
    
    ' 親フォルダのパスを相対パス記法で指定
    Dim parentFolderPath As String
    parentFolderPath = currentPath & "\.."
    
    ' 結果をメッセージボックスで表示
    MsgBox "現在のフォルダ: " & currentPath & vbCrLf & _
           "親フォルダのパス: " & parentFolderPath
End Sub

この基本的な実装では、以下の処理が行われます。

  1. 現在のワークブックの場所を取得: ThisWorkbook.Pathでフォルダパスを取得
  2. 相対パス記法で親フォルダを指定: 「\..」を追加して親フォルダを表現
  3. 結果の確認: メッセージボックスで両方のパスを表示

ThisWorkbook.Path の特徴

ThisWorkbook.Pathは、マクロが記述されているワークブック自身のフォルダパスを返します。他のワークブックが開かれていても、常にこのマクロを含むファイルの場所を取得できる点が重要です。

基本実装の課題

上記の基本実装には、以下の課題があります。

  • 相対パス表記のまま: パスに「..」が含まれたままで分かりにくい
  • エラー処理なし: ファイルが保存されていない場合にエラーが発生する可能性
  • 汎用性の不足: 一つ上の階層に限定されている

これらの課題を解決するために、より堅牢な実装方法を次に紹介します。

相対パスと絶対パスの理解

相対パスと絶対パスの違い

パスの表現方法には、大きく分けて2つの種類があります。

種類 特徴
絶対パス ドライブルートからの完全なパス C:\Users\UserName\Documents
相対パス 現在の場所からの相対的なパス ..\Documents

絶対パス変換の必要性

相対パス(C:\Work\Project\..)は人間には理解しにくく、他のプログラムやシステムで正しく認識されない場合があります。そのため、絶対パスC:\Work)に変換することが推奨されます。

FileSystemObjectを活用した絶対パス変換

' 指定した相対パスを絶対パスに変換して返す関数
' relativePath: 変換したい相対パスを指定
Function GetAbsolutePath(ByVal relativePath As String) As String

    On Error GoTo ErrorHandler
    
    ' FileSystemObjectのインスタンスを作成(参照設定を追加した場合の書き方)
    Dim fso As New FileSystemObject
    
    ' 相対パスを絶対パスに変換
    GetAbsolutePath = fso.GetAbsolutePathName(relativePath)
    
    ' 正常終了時のリソース解放処理へ移動
    GoTo Cleanup
    
ErrorHandler:
    ' エラーが発生した場合は空文字を返す
    GetAbsolutePath = ""
    Debug.Print "パス変換エラー: " & Err.Description
    Err.Clear
    
Cleanup:
    ' FileSystemObjectのリソースを解放
    If Not fso Is Nothing Then Set fso = Nothing
End Function

参照設定について、さらに詳しく知りたい方は、私が書いた記事
第10回: Excel VBAにおけるFileSystemObjectを活用した高度なファイル操作」もぜひご覧ください。

処理の詳細解説

  1. FileSystemObjectの作成

     ' FileSystemObjectのインスタンスを作成(参照設定を追加した場合の書き方)
     Dim fso As New FileSystemObject
    

    ファイルシステム操作用のオブジェクトを作成します。

  2. 絶対パス変換の実行

    GetAbsolutePath = fso.GetAbsolutePathName(relativePath)
    

    GetAbsolutePathNameメソッドが相対パスを絶対パスに自動変換します。

  3. エラーハンドリング設計

    • エラー発生時は空文字("")を返すことで、呼び出し元で判定可能
    • Debug.Printでエラー内容をイミディエイトウィンドウに出力
  4. 適切なリソース管理

    • GoTo Cleanupパターンでリソース解放コードを統一
    • 正常時もエラー時も確実にオブジェクトを解放

GetAbsolutePathName メソッドの働き

このメソッドは、「C:\Work\Project\..」のような相対パス表記を「C:\Work」のような分かりやすい絶対パスに自動変換してくれます。ファイルが実際に存在しなくても、パス文字列の変換のみを行います。

エラーハンドリングとセキュリティ考慮事項

親フォルダパス取得処理では、様々なエラー状況が発生する可能性があります。安定したマクロを作成するために、これらのエラーパターンを理解し、適切な対策を講じることが重要です。

よくあるエラーパターンと対策

親フォルダパス取得処理で発生しやすいエラーと、その対策方法を整理します。

エラー状況 原因 対策
パスが空文字 新規ワークブックが未保存 事前チェックで早期リターン
アクセス権限エラー フォルダへの読み取り権限なし 権限チェック関数の追加
ドライブルートの親 C:\ の親フォルダを要求 ルートフォルダの判定処理

堅牢な親フォルダパス取得関数の実装

実際のマクロでは、上記のエラー状況に対応できる関数を作成することが重要です。以下は、エラー処理とセキュリティを考慮した実用的な実装例です。

' 現在のワークブックの親フォルダパスを安全に取得する関数
Function GetParentFolderPathSafely() As String

    ' 入力値チェック: ワークブックが未保存の場合は早期リターン
    If ThisWorkbook.Path = "" Then
        MsgBox "ファイルが保存されていません。先に保存してから実行してください。", vbExclamation
        GetParentFolderPathSafely = ""
        Exit Function
    End If
    
    On Error GoTo ErrorHandler
    
    ' FileSystemObjectのインスタンスを作成(参照設定を追加した場合の書き方)
    Dim fso As New FileSystemObject
    
    ' 現在のワークブックのフォルダパスを取得
    Dim currentPath As String
    currentPath = ThisWorkbook.Path
    
    ' ドライブのルートフォルダかどうかを判定(例: C:\の場合)
    If fso.GetParentFolderName(currentPath) = "" Then
        MsgBox "現在のフォルダはドライブのルートフォルダです。親フォルダは存在しません。", vbInformation
        GetParentFolderPathSafely = ""
        GoTo Cleanup
    End If
    
    ' 親フォルダの絶対パスを取得
    Dim parentPath As String
    parentPath = fso.GetAbsolutePathName(currentPath & "\..")
    
    ' 親フォルダへのアクセス権限を確認
    If Not fso.FolderExists(parentPath) Then
        MsgBox "親フォルダにアクセスできません。権限を確認してください。", vbCritical
        GetParentFolderPathSafely = ""
        GoTo Cleanup
    End If
    
    ' 正常に取得できた場合は結果を返す
    GetParentFolderPathSafely = parentPath
    GoTo Cleanup
    
ErrorHandler:
    ' エラーが発生した場合の処理
    MsgBox "パス取得中にエラーが発生しました: " & Err.Description, vbCritical
    GetParentFolderPathSafely = ""
    Err.Clear
    
Cleanup:
    ' メモリリークを防ぐためリソースを解放
    If Not fso Is Nothing Then Set fso = Nothing
End Function

セキュリティ上の注意点

パス操作の安全性
文字列の直接操作ではなく、FileSystemObjectの標準メソッドを使用することで、パス操作時のセキュリティリスクを軽減できます。特に、ユーザー入力を含むパスを扱う場合は注意が必要です。

権限の最小化原則
取得した親フォルダパスを使用する際は、必要最小限の権限でアクセスするよう心がけます。読み取り専用で十分な場合は、書き込み操作を避けることが重要です。

実用的な使用例

' 安全な親フォルダパス取得の使用例
Sub UseParentFolderPath()
    
    ' 安全に親フォルダパスを取得
    Dim parentPath As String
    parentPath = GetParentFolderPathSafely()
    
    ' 取得に失敗した場合は処理を中断
    If parentPath = "" Then
        Exit Sub
    End If
    
    ' 正常に取得できた場合の処理を続行
    MsgBox "親フォルダパス: " & parentPath
    
End Sub

このように、エラー処理を適切に実装することで、様々な環境や状況でも安定して動作するマクロを作成できます。

より階層の深い親フォルダの取得

2階層以上上のフォルダにアクセスしたい場合の応用例です。

' 指定したフォルダパスから指定階層分上のフォルダの絶対パスを取得する関数
' folderPath: 基準となるフォルダのパスを指定
' levelsUp: 何階層上のフォルダまでさかのぼるかを指定
Function GetAncestorPath(ByVal folderPath As String, ByVal levelsUp As Long) As String

    On Error GoTo ErrorHandler
    
    ' 入力値の妥当性チェック
    If folderPath = "" Or levelsUp < 1 Then
        GetAncestorPath = ""
        Exit Function
    End If
    
    ' FileSystemObjectのインスタンスを作成(参照設定を追加した場合の書き方)
    Dim fso As New FileSystemObject
    
    ' 指定回数分「\..」を追加
    Dim relativePath As String
    relativePath = folderPath
    
    Dim i As Long
    For i = 1 To levelsUp
        relativePath = relativePath & "\.."
    Next i
    
    ' 絶対パスに変換
    GetAncestorPath = fso.GetAbsolutePathName(relativePath)
    
    GoTo Cleanup
    
ErrorHandler:
    GetAncestorPath = ""
    Debug.Print "上位フォルダパス取得エラー: " & Err.Description
    Err.Clear
    
Cleanup:
    If Not fso Is Nothing Then Set fso = Nothing
End Function

使用例

' 2階層上のフォルダパスを取得
Dim ancestorPath As String
ancestorPath = GetAncestorPath(ThisWorkbook.Path, 2)

階層指定の活用場面

プロジェクト管理で、以下のような構造を持つ場合に有効です。

プロジェクトルート\
├── docs\
├── data\
└── tools\
    └── excel\
        └── analysis.xlsm  ← 現在のファイル

この場合、GetAncestorPath(ThisWorkbook.Path, 2)でプロジェクトルートにアクセスできます。

まとめ

今回解説した親フォルダパス取得テクニックは、環境に依存しない柔軟なExcelマクロの作成において重要な基盤技術です。このテクニックを活用することで、「ファイルの移動や配布のたびにパスを書き換える」という従来の煩雑な作業から解放され、どの環境でも自動的に適切なフォルダ構造を認識して動作する真にポータブルなマクロシステムを実現できます。

この手法の核心となるのは、ThisWorkbook.Pathによる現在位置の自動取得、相対パス記法「..」を活用した階層移動の表現、そしてFileSystemObjectを活用した安全で信頼性の高いパス操作です。これらの技術要素を組み合わせることで、設定ファイルの読み込み、テンプレートフォルダへのアクセス、複数階層の上位フォルダ取得など、様々な場面で応用可能な汎用的なシステムを構築できます。

実装時に特に重要なのは、適切なエラーハンドリングとセキュリティ考慮事項の徹底です。ファイルが未保存の場合やアクセス権限がない場合でも、適切なメッセージでユーザーに状況を伝え、関数として分離した設計により再利用性と保守性を確保することで、実用的で堅牢なマクロを作成できます。また、絶対パス変換により分かりやすく扱いやすいパス形式への統一を図ることで、他のシステムとの連携時にも問題が発生しにくい設計となります。

また、関数として分離した設計により、再利用性と保守性を確保できます。設定ファイルの読み込み、テンプレートフォルダへのアクセス、複数階層の上位フォルダ取得など、様々な場面で応用可能です。

次回は、Excel VBAの独自イベントについて詳しく解説します!WithEventsキーワードを使ったイベントの受信方法からRaiseEventでの通知機能まで、従来の手続き型プログラミングでは実現困難だった「処理の進行状況をリアルタイムで表示」「データ変更を他のモジュールに自動通知」といった機能を完全自動化できる手法をご紹介します。クラスという設計図の基本概念から始まり、データ検証や進捗表示などの例も交えながら、疎結合で保守しやすいコード設計のテクニックが身につくイベント駆動プログラミングの基礎を解説する予定です。ぜひご期待ください!

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?