[[20140918210837]] 『複数のhtmlファイルのデータをひとつのエクセルフ』(Noro) ページの最後に飛ぶ

[ 初めての方へ | 一覧(最新更新順) | 全文検索 | 過去ログ ]

 

『複数のhtmlファイルのデータをひとつのエクセルファイルにしたい』(Noro)

いつもお世話になります。
PC内にある複数のhtmlファィル(年度別にチャートのようなデータが入っています)
をエクセルのファイルにまとめたいのですが、具体的にはエクセルで1つめのhtmlファイルのデータを読み込んで、その下の行から次のhtmlデータを取り込むものです。
ファイル名は1979.htm〜2014.htmになっています。
ひとつずつ読み込んでその都度うしろに貼り付けているのですが、なにかいい方法はありますか。一括でもいいし、その都度次のファイルを選択して追加してゆく方法でもいいと思っています。

< 使用 Excel:Excel2013、使用 OS:Windows7 >


 >ひとつずつ読み込んでその都度うしろに貼り付けているのですが、

 どのような方法で読み込んでいるのでしょう? 
(カリーニン) 2014/09/18(木) 21:32

エクセルの「開く」からPCフォルダにあるhtmlファイルを選択して読み込んでいます。
その後、ドラッグでも読み込めることがわかりました。
この方法ではひとつのhtmlに対しエクセルのbookひとつずつになるため、貼り付け追加してゆくことになります。
(Noro) 2014/09/18(木) 21:58

 WEBクエリは使えますか?

 Webの表を取り込む
http://www.excel.studio-kazu.jp/mag2/backnumber/mm20041019.html

 使えるのだったら自動化(マクロによる自動化も含む)や最終行の下への追記がしやすいのですが。
(カリーニン) 2014/09/19(金) 08:13

HTMLの内容次第なので、ご自身で調整してもらうしかないのですが、
とりあえず<TABLE>タグから片っ端から抜き出す例。

Private Declare Sub Sleep Lib "kernel32" (ByVal dwMilliseconds As Long)

 Sub test()
    Dim IE As Object
    Dim i As Long
    Dim j As Long
    Dim k As Long
    Dim iR As Long
    Dim cPath As String
    Dim cFile As String

    iR = 2
    cPath = "c:\tmp\"

    Set IE = CreateObject("InternetExplorer.application")
    IE.Visible = True

    cFile = Dir(cPath & "*.html")
    While cFile <> ""
        IE.Navigate (cPath & cFile)
        Call sWait(IE)
        With IE.document
            For i = 0 To .getElementsByTagName("TABLE").Length - 1
                For j = 0 To .getElementsByTagName("TABLE")(i).getElementsByTagName("TR").Length - 1
                    For k = 0 To .getElementsByTagName("TABLE")(i).getElementsByTagName("TR")(j).getElementsByTagName("TD").Length - 1
                        Cells(iR, k + 1).Value = .getElementsByTagName("TABLE")(i).getElementsByTagName("TR")(j).getElementsByTagName("TD")(k).innerHTML
                    Next k
                    iR = iR + 1
                Next j
            Next i
        End With
        cFile = Dir
    Wend

    IE.Quit
    Set IE = Nothing
End Sub

 Sub sWait(OBJ As Object)
    Sleep 1000
    While OBJ.readyState <> 4
        While OBJ.Busy = True
            DoEvents
            Sleep 100
        Wend
    Wend
    Sleep 1000
End Sub
(???) 2014/09/19(金) 10:35

カリーニンさん、ありがとうございます。
WEBクエリは使えることは使えますが、サイトのWEBから取り込むのではなく、すでにPCに存在するhtmlファィル(E:\)を取り込むのですが、これもクエリが使えるのでしょうか。

???さん、ありがとうございます。
このマクロでとりあえず使ってみたのですが、htmlファイルがとりあえず立ち上がりましたが、エクセル上では
Sleep 1000のところで定義がないということで止まってしまいました。
sWaitのマクロはなにを意味するのでしょうか。
またPrivate Declare Sub Sleep Lib "kernel32" (ByVal dwMilliseconds As Long) はSub test()の前に必要ですか?(外して作ったのですが)

htmlは表のタイトルは別として
表は

    <table width="650" border="1" align="center">
      <tr class="tabletitle">             
        <td width="25">順位</td> 
        <td width="50">得点</td>             
        <td width="300">C</td>             
        <td width="175">D</td>             
        <td width="94">日付</td>             
  </tr>             
  <tr>             
        <td width="25" align="center">1</td> 
        <td width="50" align="center">159.6</td>           
        <td width="300">C</td>          
        <td width="175">D</td>          
        <td width="94" align="center">1966/3/24</td>          
  </tr>    
以下続く
のようになっています。
ファイルパスはE:\1979.htm〜E:\1990.htmのようになります。

(Noro) 2014/09/20(土) 14:03


 >WEBクエリは使えることは使えますが、サイトのWEBから取り込むのではなく、
 >すでにPCに存在するhtmlファィル(E:\)を取り込むのですが、これもクエリが使えるのでしょうか。 

 私がお聞きしたかったのは、WEBクエリの使い方を知っているか、ということではなく、実際に
 WEBクエリでPC上のHTMLファイルを取り込めるか否か、ということです。
 ですので、ご自身で取り込み作業をして取り込めるか否かを確認してください。

 >またPrivate Declare Sub Sleep Lib "kernel32" (ByVal dwMilliseconds As Long) はSub test()の前に必要ですか?
 >(外して作ったのですが) 

 必要だから記述されています。
 この宣言がないとSleepは使えません。
(カリーニン) 2014/09/20(土) 15:26

 >sWaitのマクロはなにを意味するのでしょうか。

 > IE.Navigate (cPath & cFile)
 でIE上でページが開くのを待つ(今回は1000ミリ秒=1秒)ための記述です。

 ページが開かないとページからデータを読み込めませんので。
(カリーニン) 2014/09/20(土) 15:30

webクエリでE:\1979.htmのデータはエクセルに入りました。

Private Declare〜
については今までマクロの1行目はSub **()で作ってもらったものばかりだったので、この記述がわかりませんでした。(当方マクロについてはほとんど知識がないためすみません)

それで入れて見たのですが、
While OBJ.readyState <> 4のところで
オートメーションエラー/インターフェイスは認識しないというメッセージになりました。
(Noro) 2014/09/20(土) 18:25


 PCに保存してあるHTMLファイルで試したら
 >オートメーションエラー
 となりました。

 通常のURL(テーブルあり)で試したら取り込むことが出来ました。
 とりあえず報告まで。
(カリーニン) 2014/09/20(土) 20:08

WEBクエリでやった場合
URLのところで、Application.Dialogs(xlDialogOpen).Showが使えれば
それをを利用してPC内ファィルを開いてデータを読み込んだら、読み込んだエクセルの最終データの後ろでまた次のWEBクエリを実行することを自動化できればよさそうですね。
(Noro) 2014/09/21(日) 08:32

 ダイアログでユーザーにファイルを指定させるのでしたら
 GetOpenFilenameメソッド
 が便利です。

 参考HPです。

 Office TANAKA - Excel VBAファイルの操作[名前を指定してブックを開く]
http://officetanaka.net/excel/vba/file/file02.htm

 この中の
 「複数のファイルを選択可能にする」
 で一つのフォルダ内の複数のファイルを指定できます。

 複数のフォルダにまたがる場合はセルや配列にファイルのパスを蓄積していくといいでしょう。
(カリーニン) 2014/09/21(日) 19:09

 一つのフォルダ内の特定の拡張子のファイル全てを対象にするのなら、
 Dir関数
 や
 FileSystemObject
 を使えば一挙に取得できます。
(カリーニン) 2014/09/21(日) 19:12

Private Declare Sub Sleep Lib "kernel32" (ByVal dwMilliseconds As Long)

この部分を説明すると、これはwindowsが持っている関数(API)の Sleep() を使うための宣言になります。
Sleep命令は、Excel VBAの機能より簡単に、しかもミリ秒単位の待ちができるので、よく利用します。

なお、IEを操作してファイル構造を読み取るので、IEが普通に起動できるか確認してください。
(よくアップデート後に、環境設定で止まったりします)
(???) 2014/09/22(月) 09:39


もう1点。IEでファイルを開く際の記述を、以下に変えてみてください。

        IE.Navigate ("file://" & cPath & cFile)
(???) 2014/09/22(月) 09:47

お手数をおかけします。
GetOpenFilenameメソッド等を読ませてもらいましたが記述の仕方はわかってもどの部分に入れたらいいやら
残念ながら素人にはよく理解できません。
またご指示のVBAについてはやはりエラーが出てしまうほか、呼び出したHTMLの内容も不要であるリンク先の部分も取り込んでしまうため視点を変えて、クエリをマクロの記録で動かしてみました。
その結果次のようなVBAになったのですが、必要ファイル分だけ繰り返したい場合、繰り返す記述とURLのところをダイアログでPC内フォルダで指定するhtmファィル名を代入できればいいと思ったのでそれをどのように記述するのかということと、書き出し位置をクエリを繰り返すごとにデータの末尾に指定する記述があればと思いましたので、その記述がわかればありがたいです。(記録ではURLは手動入力です)

    With ActiveSheet.QueryTables.Add(Connection:="URL;file:///E:/1979.htm", _
'※file:///E:/1979.htmをダイアログで任意のファイルを選び代入したい

        Destination:=Range("$A$1"))
※$A$107"の位置は前のクエリで取り込んだデータの次からにしたい
        .Name = "1979"
        .FieldNames = True
        .RowNumbers = False
        .FillAdjacentFormulas = False
        .PreserveFormatting = True
        .RefreshOnFileOpen = False
        .BackgroundQuery = True
        .RefreshStyle = xlInsertDeleteCells
        .SavePassword = False
        .SaveData = True
        .AdjustColumnWidth = True
        .RefreshPeriod = 0
        .WebSelectionType = xlEntirePage
        .WebFormatting = xlWebFormattingNone
        .WebPreFormattedTextToColumns = True
        .WebConsecutiveDelimitersAsOne = True
        .WebSingleBlockTextImport = False
        .WebDisableDateRecognition = False
        .WebDisableRedirections = False
        .Refresh BackgroundQuery:=False
    End With

(以下繰り返し)

    ActiveCell.Offset(106, 0).Range("A1").Select
    With ActiveSheet.QueryTables.Add(Connection:="URL;file:///E:/1980.htm", _
        Destination:=Range("$A$107"))
        .Name = "1980"
        .FieldNames = True

(Noro) 2014/09/22(月) 12:01


新案のほうを、とりあえず整形してみただけ。

 Sub test()
    Dim cFile As Variant
    Dim iR As Long

    iR = Cells(Rows.Count, "A").End(xlUp).Row + 1

    cFile = Application.GetOpenFilename()
    If cFile = False Then
        Exit Sub
    End If
    cFile = Replace(cFile, "\", "/")

    With Me.QueryTables.Add(Connection:="URL;file:///" & cFile, Destination:=Me.Range("$A$" & iR))
        .Name = cFile
        .FieldNames = True
        .RowNumbers = False
        .FillAdjacentFormulas = False
        .PreserveFormatting = True
        .RefreshOnFileOpen = False
        .BackgroundQuery = True
        .RefreshStyle = xlInsertDeleteCells
        .SavePassword = False
        .SaveData = True
        .AdjustColumnWidth = True
        .RefreshPeriod = 0
        .WebSelectionType = xlEntirePage
        .WebFormatting = xlWebFormattingNone
        .WebPreFormattedTextToColumns = True
        .WebConsecutiveDelimitersAsOne = True
        .WebSingleBlockTextImport = False
        .WebDisableDateRecognition = False
        .WebDisableRedirections = False
        .Refresh BackgroundQuery:=False
    End With
End Sub
(???) 2014/09/22(月) 14:17

ありがとうございます。
今回のものでは
Me.RangeのMe.ところで「キーワードが不正」となりました。
(Noro) 2014/09/22(月) 14:47

シートモジュールに記述するマクロですが、標準モジュールに貼りましたか?
その場合 Me を、Sheets("Sheet1") 等に置き換えてください。

または、Me. を削ってしまっても良いですが、これだと開いたファイルのほうに貼りそう。
(???) 2014/09/22(月) 15:10


自動記録したのだから、標準モジュールなのが当たり前でしたね。すいません。こんな感じで。

 Sub test()
    Dim cFile As Variant
    Dim iR As Long

    iR = Cells(Rows.Count, "A").End(xlUp).Row + 1

    cFile = Application.GetOpenFilename()
    If cFile = False Then
        Exit Sub
    End If
    cFile = Replace(cFile, "\", "/")

    With ActiveSheet.QueryTables.Add(Connection:="URL;file:///" & cFile, Destination:=Range("$A$" & iR))
        .Name = cFile
        .FieldNames = True
        .RowNumbers = False
        .FillAdjacentFormulas = False
        .PreserveFormatting = True
        .RefreshOnFileOpen = False
        .BackgroundQuery = True
        .RefreshStyle = xlInsertDeleteCells
        .SavePassword = False
        .SaveData = True
        .AdjustColumnWidth = True
        .RefreshPeriod = 0
        .WebSelectionType = xlEntirePage
        .WebFormatting = xlWebFormattingNone
        .WebPreFormattedTextToColumns = True
        .WebConsecutiveDelimitersAsOne = True
        .WebSingleBlockTextImport = False
        .WebDisableDateRecognition = False
        .WebDisableRedirections = False
        .Refresh BackgroundQuery:=False
    End With
End Sub
(???) 2014/09/22(月) 15:24

何度もありがとうございました。これで無事読み込むことができました。繰り返したいのでFor i とNextを入れたところうまくゆきました。
ところでこれを解読しているのですが、開くフォルダのE:\というのがどうしても読み取れません。たとえば読み取るフォルダをD:\DATAにしたい場合、その位置がわかると直しやすいのですが、どこで指示しているのでしょうか。(最初のだとcPathというのがあったのでそれを直したのですが。)
(Noro) 2014/09/22(月) 15:49

Application.GetOpenFilename() を使用しているので、これでEドライブを指定して開くだけですが?
1ファイル指定するものなので、繰り返しているという状況がよく判りません。

もし、ダイアログの初期位置をE:にしたいのならば、Excelでは難しいので、諦めてください。
(クラスモジュールを利用してコールバックアドレスを指定すれば実現できそうな気がしますが…)
(???) 2014/09/22(月) 16:35


Application.GetOpenFilename() はドライブ全体だったですね。ここからEドライブを開けばいいことがわかりました。ダイアログで指定できなくても最初にそのフォルダに行けば続けることで同じフォルダば連続して表示できるのでこれで間に合います。

繰り返しているという状況…
iR = Cells
の前に
For i = 1 To 15 Step 1を入れ、End subの前にNextを入れました。
この結果、最初に指定した1968.htmがエクセルに読み込まれたあと、再度ダイアログが開くので、1969.htmを選択実行すると、エクセル上では1968のデータの次に1969のデータが追加できました。これを繰り返すことで複数のhtml(〜1980)を1つのbookにしてしまうことができました。
当初の希望どおりにできましたのでありがとうございました。

(Noro) 2014/09/22(月) 17:41


コメント返信:

[ 一覧(最新更新順) ]


YukiWiki 1.6.7 Copyright (C) 2000,2001 by Hiroshi Yuki. Modified by kazu.