Excel VBA質問箱 IV

当質問箱は、有志のボランティア精神のおかげで成り立っています。
問題が解決したら、必ずお礼をしましょうね。
本サイトの基本方針をまとめました。こちら をご一読ください。

投稿種別の選択が必要です。ご注意ください。
迷惑投稿防止のため、URLの入力を制限しています。ご了承ください。


2391 / 13646 ツリー ←次へ | 前へ→

【68283】ファイル名を取得するマクロの意味 えっちゃん 11/2/20(日) 16:13 質問[未読]
【68284】Re:ファイル名を取得するマクロの意味 かみちゃん 11/2/20(日) 16:48 発言[未読]
【68296】Re:ファイル名を取得するマクロの意味 kanabun 11/2/21(月) 12:21 発言[未読]
【68302】Re:ファイル名を取得するマクロの意味 kanabun 11/2/21(月) 21:05 発言[未読]
【68310】Re:ファイル名を取得するマクロの意味 neptune 11/2/22(火) 11:17 発言[未読]
【68319】Re:ファイル名を取得するマクロの意味 kanabun 11/2/23(水) 19:25 発言[未読]
【68320】Re:ファイル名を取得するマクロの意味 neptune 11/2/23(水) 21:54 発言[未読]
【68311】Re:ファイル名を取得するマクロの意味 neptune 11/2/22(火) 11:24 発言[未読]

【68283】ファイル名を取得するマクロの意味
質問  えっちゃん  - 11/2/20(日) 16:13 -

引用なし
パスワード
   手作業でフォルダの中のファイルの名前を1つずつExcelシートの
コピーペーストしていたところ、先輩からこのマクロボタンで一瞬でできるよ
と言われました。
おかげですぐに作業が終わったのですが、これを機にマクロを覚えようと勉強を始めました。
ただ、マクロが難解で私の持っている本ではおぼつかないのです。
先輩に聞きたいところですが、プロジェクトリーダーされていて多忙で、質問しにくいのです。
もしよろしければ1行ずつ何をしているのか解説いただいてもいいでしょうか。


Option Explicit
Public cnt, Pop As Integer
Sub macro1()

  Dim FolderSpec As String
  
  FolderSpec = FolderPath
  
  cnt = 1
  Pop = 1

  If FolderSpec <> "" Then
    Lists FolderSpec
  End If

End Sub


Sub Lists(FolderSpec)

  Dim File_Collection As Object
  Dim File_List As Variant
  Dim Folder_Collection As Object
  Dim Folder_List As Variant
  
  Set File_Collection = CreateObject("Scripting.FileSystemObject").GetFolder(FolderSpec).Files
  
  'Foldor の名前をセルに入力
  Cells(cnt, Pop) = FolderSpec
  cnt = cnt + 1

  For Each File_List In File_Collection

    Cells(cnt, Pop + 1) = File_List.Name
    cnt = cnt + 1
  Next
  
  Set Folder_Collection = CreateObject("Scripting.FileSystemObject").GetFolder(FolderSpec).SubFolders
  
  For Each Folder_List In Folder_Collection
    Pop = Pop + 1
    Lists FolderSpec & "\" & Folder_List.Name
  Next
  Pop = Pop - 1
End Sub


Function FolderPath() As String
  
  Dim Shell As Object
  
  Set Shell = CreateObject("Shell.Application").BrowseForFolder(0, "フォルダを選択してください", 0, "C:\Documents and Settings\Others")
  
  If Shell Is Nothing Then
    FolderPath = ""
  Else
    FolderPath = Shell.Items.Item.Path
  End If

End Function

【68284】Re:ファイル名を取得するマクロの意味
発言  かみちゃん E-MAIL  - 11/2/20(日) 16:48 -

引用なし
パスワード
   こんにちは。かみちゃん です。

>もしよろしければ1行ずつ何をしているのか解説いただいてもいいでしょうか。

まずは、以下を参照してみてください。
ht tp://www.k1simplify.com/vba/tipsleaf/leaf280.html
ht tp://www.k1simplify.com/vba/tipsleaf/leaf270.html

そして、1行ずつ解説を求める前に、ヘルプやWebで自分で調べたものを載せて
みてください。

そのほうが必ず、チカラになります。

説明するのは、簡単な場合もありますが、理解していただけるように説明するのは、
その方のスキル等を知らないと、かなり難しいと思います。

冷たいように聞こえるかもしれませんが、
まずは、自分で調べたことを書いてみてください。

ひとふんばり、がんばってください。

【68296】Re:ファイル名を取得するマクロの意味
発言  kanabun  - 11/2/21(月) 12:21 -

引用なし
パスワード
   ▼えっちゃん さん:こんにちは〜

>おかげですぐに作業が終わったのですが、これを機にマクロを覚えようと勉強を始めました。

まず FileSystemObject についてある程度の知識が必要と思われます。
このプログラムのポイントは
FileSystemObjectオブジェクトの GetFolderメソッド
を使って、
「指定フォルダ内の Filesコレクションと SubFoldersコレクション
を取得」しているところにあるように思われます。

つぎに、SubFoldersコレクションを得たら、それぞれのSubFolderについて
また「指定フォルダ内の Filesコレクションと SubFoldersコレクション
を取得」するために、《自身を呼び出し》ています。これが再帰呼び出し
とよばれ、プログラミングでも結構高度な処理なのです。

'参考までに、
同じ処理を 別の書き方で記述してみましたので、
元のコードと比較してみてください。

--------------------------------------------------------
Option Explicit

'指定フォルダのファイル名を(サブフォルダも含めて)シートに書き出す
Sub Macro2()
  Dim TopFolder As String

  '調べる先頭フォルダを選択します
  TopFolder = フォルダを指定する()
  If Len(TopFolder) = 0 Then Exit Sub
  
  Cells.Clear
  '先頭フォルダについてフォルダ情報を取得します
  ■フォルダ情報 TopFolder, 0, 1

End Sub

Sub ■フォルダ情報(FolderName As String, n As Long, Level As Long)
  Dim objFolder As Object
  Dim myFile As Variant
  Dim myFolder As Variant
  
  'Foldor の名前をセルに書き出します
  n = n + 1
  Cells(n, Level) = FolderName
 
  Set objFolder = CreateObject("Scripting.FileSystemObject") _
         .GetFolder(FolderName)
  
  'Folder内のファイルを取得します →セルに書き出します
  For Each myFile In objFolder.Files
    n = n + 1
    Cells(n, Level + 1) = myFile.Name
  Next

  'こんどは Folder内のSubFolder についてフォルダ情報を取得します
  For Each myFolder In objFolder.SubFolders
    Level = Level + 1
    ■フォルダ情報 FolderName & "\" & myFolder.Name, n, Level
  Next
  Level = Level - 1
End Sub

Function フォルダを指定する() As String
  Dim Shell As Object

  Set Shell = CreateObject("Shell.Application"). _
     BrowseForFolder(0, "フォルダを選択してください", _
     0, CreateObject("WScript.Shell").SpecialFolders("desktop"))

  If Shell Is Nothing Then
    フォルダを指定する = ""
  Else
    フォルダを指定する = Shell.Self.Path
  End If

End Function

【68302】Re:ファイル名を取得するマクロの意味
発言  kanabun  - 11/2/21(月) 21:05 -

引用なし
パスワード
   ▼えっちゃん さん:

>Option Explicit
>Public cnt, Pop As Integer

原作のPublic変数の宣言ですが、
たぶん

Public cnt As Long, Pop As Integer

のまちがいかと思います。
(変数を宣言したら直後にデータ型をいちいち宣言しないと、その変数は
単に Variant型となる)

あと、個人的には、なるべくモジュールレベル変数を使わないように
したほうが、コードの可読性が高まると思います。

【68310】Re:ファイル名を取得するマクロの意味
発言  neptune  - 11/2/22(火) 11:17 -

引用なし
パスワード
   ▼kanabun さん:
横から失礼

>Function フォルダを指定する() As String
>  Dim Shell As Object

shellって変数名、shell関数がありますから予約語と思います。
このケースで問題があるかないかは知りませんが、避けるべきでは?
・・・基本的に予約語は使用しないという意味で。

【68311】Re:ファイル名を取得するマクロの意味
発言  neptune  - 11/2/22(火) 11:24 -

引用なし
パスワード
   ▼kanabun さん:
連投すみません。最初に提示されたソースからそうなってますね。
でも、他の名前にした方が良いですね。

【68319】Re:ファイル名を取得するマクロの意味
発言  kanabun  - 11/2/23(水) 19:25 -

引用なし
パスワード
   ▼neptune さん:

>shellって変数名、shell関数がありますから予約語と思います。
>このケースで問題があるかないかは知りませんが、避けるべきでは?
>・・・基本的に予約語は使用しないという意味で。

書いたときは気にしてなかったけど、
言われてみると気になりますね(^^

ただ、本来の「予約語」はそもそも使いたくても、コンパイルを通りません。
井川はるきさんによると、具体的には以下のもの(抜けがあったらすみません)
が予約語で、
識別子として認識されるものだそうです。

AddressOf
And
As
Attribute
Boolean
ByRef
Byte
ByVal
Case
CBool
CByte
CCur
CDate
CDbl
CInt
CLng
Close
Const
CSng
CStr
Currency
CVar
CVErr
Date
Debug
Declare
Dim
Do
Double
Each
Else
ElseIf
Empty
End
Enum
Eqv
Erase
Event
Exit
False
For
Friend
Function
Get
GoSub
GoTo
If
Imp
Implements
In
Input
Integer
Is
LBound
Len
Let
Like
Lock
Long
Loop
LSet
Me
Mod
New
Next
Not
Nothing
Null
On
Open
Or
Option
Optional
ParamArray
Print
Private
Public
Put
RaiseEvent
Resume
Return
RSet
Seek
Select
Set
Single
Spc
Static
Stop
String
Sub
Tab
Then
To
True
Type
TypeOf
UBound
Unlock
Variant
Wend
While
With
WithEvents
Write
Xor

【68320】Re:ファイル名を取得するマクロの意味
発言  neptune  - 11/2/23(水) 21:54 -

引用なし
パスワード
   ▼kanabun さん:
ちょっと脱線気味の内容ではありますけど

>書いたときは気にしてなかったけど、
>言われてみると気になりますね(^^
はい、気になります。
私もkanabun さんのようなハイレベルの方が知っていて使う分には
気にならないのですが、
いかんせん初心者の方には不適当です。

>ただ、本来の「予約語」はそもそも使いたくても、コンパイルを通りません。
本来の「予約語」ってのがよくわかりませんけど、
予約語って、言語、ライブラリなどによって既に定義されている単語である
と考える(そういう考え方はあります)とShellは
VBA.interactionのメンバであり、Shell関数として定義されています。
VBA.interaction.shell
そういう意味では予約語と言っても間違いはないと思います。

まぁ、今回はプロシージャレベルのスコープの変数定義ですし、そのスコープ
内でShell関数も使ってないからエラーは発生しないようですが、これが
モジュールレベル以上でのスコープを持った場合でshell関数を使ったときは
どうなるんでしょ?
(検証はしてません。)
・・・・と不安にならない為にも特に初心者の方には指摘しておいた方が
良いと思います。


所で、スレ主の方は・・・・見てるのかな。

2391 / 13646 ツリー ←次へ | 前へ→
ページ:  ┃  記事番号:
2610219
(SS)C-BOARD v3.8 is Free