返回列表 上一主題 發帖

證交所全部上市股票交易明細下載

本帖最後由 GBKEE 於 2012-8-5 09:23 編輯

回復 1# white5168
測試 完成圖


2012/8/5 更新程式碼
   
  1. Option Explicit
  2. Dim SH(1 To 2) As Worksheet, IE As Object
  3. Dim xltheCsv As String, xLMsg As String, Rng As Range
  4. Const xlPath = "D:\Test1\"                  '可修改CSV存檔的路徑
  5. Sub 全部日報表()                            '查詢全部日股票報表
  6.     Dim T As Date
  7.     存檔資料夾
  8.     T = Time
  9.     xLMsg = ""                              '紀錄 股票代號沒報表
  10.     上市股票代號                            '取得最新上市股票代號表
  11.     網頁                                    '開啟網頁
  12.     Set Rng = SH(1).[A3]                    '股票代號
  13.     Do
  14.         Rng.Select
  15.         ActiveWindow.ScrollRow = Rng.Row - 1
  16.         Application.ScreenUpdating = False
  17.         If Rng.Offset(, 1) <> "" Then 匯入日報表 Trim(Split(Rng, " ")(0))                                            'Trim(Split(Rng, " ")(0)):股票代號
  18.         Set Rng = Rng.Offset(1)             '下一個 股票代號
  19.         Application.ScreenUpdating = True
  20.     'Loop Until Rng = ""                    '<-含   上市股票,上市認購(售)權證,受益證券-不動產投資信託--
  21.     Loop Until Rng.Offset(, 1) = ""         '<-僅有 上市股票 : B欄是空白時離開迴圈
  22.     SH(1).Parent.Close 0                    '關閉 最新上市股票代號表
  23.     IE.Quit                                 '關閉 網頁
  24.     Set IE = Nothing
  25.     Set Rng = Nothing
  26.     MsgBox "全部日報表下載完成 費時" & Format(T - Time, "HH時mm分ss秒") & Chr(10) & xLMsg
  27.     If xLMsg <> "" Then 無報表紀錄
  28. End Sub
  29. Sub 查詢股票日報表()                        '查詢單一股票日報表
  30.     Dim 股票代號 As String, 股票 As String, T As Date
  31.     存檔資料夾
  32.     xLMsg = ""
  33.     Do While 股票代號 = ""
  34.         股票代號 = InputBox("股票代號", "輸入查詢之股票代號", "1101")
  35.         If 股票代號 = "" Then End
  36.     Loop
  37.     T = Time
  38.     網頁
  39.     匯入日報表 股票代號
  40.     IE.Quit
  41.     Set IE = Nothing
  42.     If xLMsg <> "" Then
  43.         MsgBox xLMsg
  44.         無報表紀錄
  45.         Exit Sub
  46.     Else
  47.         股票 = Replace(Replace(xltheCsv, ".CSV", ""), xlPath, "")
  48.         MsgBox 股票 & Chr(10) & "下載時間" & Format(T - Time, "HH時mm分ss秒") _
  49.         & Chr(10) & "存檔路徑: " & xlPath
  50.     End If
  51.     Workbooks.Open xltheCsv
  52.     ActiveSheet.Cells.EntireColumn.AutoFit
  53. End Sub
  54. Private Sub 匯入日報表(股票代號 As String)      '處裡傳送來的 --股票代號--
  55.     Dim Xall As Integer, SubMsg As String, SubRng As Range
  56.     Xall = Val(報表頁數(股票代號))              '傳回報表頁數
  57.     If Xall = 0 Then                            '無報表頁數: 報表不存在
  58.         If Rng Is Nothing Then
  59.             SubMsg = "[ " & 股票代號 & " ] 無報表"
  60.         Else                                    '全部日報表程式: 含股票名稱
  61.             SubMsg = Rng & " 無報表"
  62.         End If
  63.         xLMsg = IIf(xLMsg <> "", xLMsg & Chr(10) & SubMsg, SubMsg)
  64.         Exit Sub
  65.     End If
  66.     Set SH(2) = Workbooks.Add(1).Sheets(1)       '新增一活頁簿
  67.     With SH(2).QueryTables.Add(Connection:="URl;http://bsr.twse.com.tw/bshtm/bsContent.aspx?StartNumber=" & 股票代號 & "&FocusIndex=All_" & Xall, Destination:=SH(2).Range("A1"))
  68.             .WebFormatting = xlWebFormattingNone
  69.             .WebTables = "4,""table2"""
  70.             On Error Resume Next                '程式還有錯誤不處裡
  71.             Do
  72.             Err.Clear                           '清除錯誤值
  73.             .Refresh BackgroundQuery:=False     'Refresh 失敗 會有錯誤值
  74.             Loop While Err > 0                  '有錯誤值繼續迴圈 直到  Refresh 成功
  75.             On Error GoTo 0                     '有錯誤值 不處裡
  76.             '消除: On Error Resume Next 如還有錯誤不處裡 會影響運行的正確性
  77.             SH(2).Names(.Name).Delete
  78.     End With
  79.     If Xall > 1 Then                              '處裡頁數 > 1  '清理空白列及 每頁的欄位
  80.         With SH(2)
  81.             Set SubRng = .Range(.[A6], .Cells(.Rows.Count, "A").End(xlUp))
  82.             SubRng.Replace "序", "", xlWhole
  83.             SubRng.SpecialCells(xlCellTypeBlanks).EntireRow.Delete xlUp
  84.         End With
  85.     End If
  86.     xltheCsv = xlPath & Format(SH(2).[B1], "yyyy_mm_dd ") & SH(2).[F1] & ".CSV"
  87.     On Error GoTo xlerr                             'xltheCsv  已開啟會有錯誤  到xLerr處裡
  88.     If Dir(xltheCsv) <> "" Then Kill xltheCsv
  89.     On Error GoTo 0
  90.     SH(2).Parent.SaveAs xltheCsv, xlCsv
  91.     SH(2).Parent.Close True
  92.     Exit Sub
  93. xlerr:
  94. If Err = 70 Then
  95.     Workbooks(Format(SH(2).[B1], "yyyy_mm_dd ") & SH(2).[F1] & ".CSV").Close 0   '關閉xltheCsv 可清除錯誤
  96.     Resume                                                                       '反回錯誤行
  97. Else
  98.     MsgBox "錯誤值 " & Err & " 需偵錯!!"
  99.     End
  100. End If
  101. End Sub
  102. Private Sub 上市股票代號()  '下載最新代號 ( 上市股票,上市認購(售)權證,受益證券-不動產投資信託 )
  103.     Dim SstockId  As String
  104.     SstockId = "URL;http://brk.twse.com.tw:8000/isin/C_public.jsp?strMode=2"
  105.     Set SH(1) = Workbooks.Add(1).Sheets(1)
  106.     With SH(1).QueryTables.Add(SstockId, SH(1).[A1])
  107.         .WebFormatting = xlWebFormattingNone
  108.         .WebTables = "2"
  109.         .Refresh 0
  110.     End With
  111. End Sub
  112. Private Sub 網頁()             '開啟網頁
  113.     Dim Url As String
  114.     Set IE = CreateObject("InternetExplorer.Application")
  115.     Url = "http://bsr.twse.com.tw/bshtm/bsMenu.aspx"
  116.     With IE
  117.         '.Visible = False   ''可以不顯示 IE
  118.           .Visible = True
  119.         .Navigate "http://bsr.twse.com.tw/bshtm/bsMenu.aspx"
  120.         Do While .Busy Or .ReadyState <> 4
  121.             DoEvents
  122.         Loop
  123.     End With
  124. End Sub
  125. Private Sub 存檔資料夾()     '沒有CSV存檔的路徑: 設立CSV存檔的路徑
  126.     If Dir(xlPath, vbDirectory) = "" Then MkDir xlPath
  127. End Sub
  128. Private Sub 無報表紀錄()   '工作表上紀錄 沒報表的股票代號
  129.     With ThisWorkbook.Sheets(1)
  130.         .Activate
  131.         If .[A1] = "" Then .[A1] = "股票: 無報表"
  132.         .Cells(.Rows.Count, "a").End(xlUp).Offset(1).Resize(UBound(Split(xLMsg, Chr(10))) + 1) = Application.Transpose(Split(xLMsg, Chr(10)))
  133.     End With
  134. End Sub
  135. Private Function 報表頁數(Sstock_N0 As String)
  136.     Dim element As Object
  137.     On Error GoTo xlerr:
  138. xlAgain:
  139.     Set element = IE.Document.getElementsByName("txtTASKNO")
  140.     element.Item(0).Value = Sstock_N0
  141.     Set element = IE.Document.getElementsByName("btnOK")
  142.     element.Item(0).Click
  143.     With IE
  144.         Do While .Busy Or .ReadyState <> 4
  145.             DoEvents
  146.         Loop
  147.     End With
  148.     Set element = IE.Document.getElementsByName("sp_ListCount")
  149.     報表頁數 = element.Item(0).innertext
  150.     Exit Function
  151. xlerr:        '處裡網頁中斷
  152.     IE.Quit
  153.     網頁
  154.     Err.Clear
  155.     GoTo xlAgain
  156. End Function
複製代碼

TOP

回復 8# HSIEN6001
回復 9# HSIEN6001
請問中斷時的錯誤值是多少

回復 10# devidlin
複製程式碼後
執行   先執行   Sub 查詢股票日報表()               再試試        Sub 全部日報表()

TOP

本帖最後由 GBKEE 於 2012-8-4 17:07 編輯

回復 13# white5168     謝謝你的提醒 指教  
回復 15# c_c_lai           回復 16# HSIEN6001  
white5168  的指教修改如下
  1. Private Function 報表頁數(Sstock_N0 As String)
  2.     Dim element As Object
  3.     On Error GoTo xlerr:
  4. xlAgain:
  5.     Set element = IE.Document.getElementsByName("txtTASKNO")
  6.     element.Item(0).Value = Sstock_N0
  7.     Set element = IE.Document.getElementsByName("btnOK")
  8.     element.Item(0).Click
  9.     With IE
  10.         Do While .Busy Or .ReadyState <> 4
  11.             DoEvents
  12.         Loop
  13.     End With
  14.     Set element = IE.Document.getElementsByName("sp_ListCount")
  15.     報表頁數 = element.Item(0).innertext
  16.     Exit Function
  17. xlerr:        '處裡網頁中斷
  18.     IE.Quit
  19.     網頁
  20.     Err.Clear
  21.     GoTo xlAgain
  22. End Function
複製代碼

TOP

回復 22# white5168
說的好理道出: 下載錯誤點的原因
多謝發表幫大眾解惑

TOP

本帖最後由 GBKEE 於 2012-8-5 07:20 編輯

回復 31# HSIEN6001
丟個沒有交易買賣的代號給它,就刷不停了,例如冷門的股票,它的交易量有可能是 " 0 ",就會出現無交易資料,當然就取不到  "頁數"


執行 7#   Sub 查詢股票日報表()    '查詢單一股票  立即可知有無交易量

7#  --- 57行  是處裡交易量是 " 0 "
54行    Private Sub 匯入日報表(股票代號 As String)      '處裡傳送來的 --股票代號--
55行    Dim Xall As Integer, SubMsg As String, SubRng As Range
56行    Xall = Val(報表頁數(股票代號))              '傳回報表頁數
57行    If Xall = 0 Then                                       '無報表頁數: 報表不存在
58行
        If Rng Is Nothing Then
--------------------------------
18# 修正的 Private Function 報表頁數(Sstock_N0 As String) 函數程式碼
可處理 :  white5168 說的如果IE沒有開完整,將會導致無法取得對應的物件
當 報表頁數 = element.Item(0).innertext  有錯誤時才會重新開啟 IE,
IE 正常時 element.Item(0).innertext=""   為無報表頁數   不嘿有錯誤產生

TOP

本帖最後由 GBKEE 於 2012-8-5 09:39 編輯

敬告各位 會員
希望各位在回文時 字句的修飾是必須的,要考慮到對方有不舒服的感受,請不要製造出互相攻擊的氛圍
在這論壇上 我真的是有感受到〔教學相長〕效應的存在

回復 39# HSIEN6001
1#   附檔有說明 :  "現在附上使用python與Excel VBA執行完成的圖案,python執行的時間2603秒,Excel VBA執行時間7598秒(未優化前),兩者相差約2.9倍"
上述的差異 39#中一段:  "Do ....Loop 會造成塞車問題。 我只是想#22樓你寫的那段;剛好與你的迴路設計是背離的"   這裡道出產生"速率的差異"

所以我 7#  的程式修正不必要的迴圈,  消除2.9倍的速率,但還是有缺點  經 white5168   指點  在18# 修改了  在這裡我就有收到 〔教學相長〕效應
你可再測試 7#  的程式看看  python執行的時間2603秒,Excel VBA執行時間7598秒 還有2.9倍的速率的差異嗎? ,
可說明 塞車問題 是否是正確的

PS: 7#的程式碼已更新同 18#  

TOP

本帖最後由 GBKEE 於 2012-8-5 09:54 編輯

回復 42# white5168
你這 未優化 與我 7# 未更新前的程式一樣 尚未測試確定沒問題就急著推出 有點類似
期待 你優化後 VBA    會 [ 教學相長 ] 的
想請教 python 也是未優化 嗎?

TOP

        靜思自在 : 有時當思無時苦,好天要積雨來糧。
返回列表 上一主題