[爆卦]vba range範圍是什麼?優點缺點精華區懶人包

為什麼這篇vba range範圍鄉民發文收入到精華區:因為在vba range範圍這個討論話題中,有許多相關的文章在討論,這篇最有參考價值!作者j2708180 (JaJa)看板Office標題[算表] VBA範圍 無法重算時間Tue Ap...



Function abc(X As Range)
Dim XR As Integer, XC As Integer

XR = X.Row
XC = X.Column

abc = Application.Average(Range(Cells(XR - 2, XC), Cells(XR, XC)))

我發現他不會自動重算!

在活頁F10輸入abc(E10) 他會計算E8:E10的平均

可是更動E8或E9的數值 他不會自動重算!

只有更改E10 或F10重新輸入 才會自動重算

即使按 立即重算 也不會重算

修改資料 但公式不會重算……

在這簡單案例中 我知道直接拉公式比較快

但我的資料計算很複雜 公式會打一堆 一更動就很難維護

要怎麼做比較好呢?

--
※ 發信站: 批踢踢實業坊(ptt.cc), 來自: 36.239.149.248 (臺灣)
※ 文章網址: https://www.ptt.cc/bbs/Office/M.1618317619.A.BC2.html
rafaiero: 是否使用儲存格變動方式,會比較適合? 04/13 21:21
是說乖乖在儲存格打公式嗎?我是把公式拆成兩格計算
soyoso: 加上 application.volatile 04/13 21:52
這個就可以自動重算,但其他無關的變化,也會讓這個公式重算?
如果這個公式用太多,可能會很慢?
soyoso: 任何儲存格變更值時,就會重新計算。也因會重新計算,因此 04/14 10:53
soyoso: 頻繁的變更值下有可能感覺效能不好。 04/14 10:53
soyoso: 回文寫"使用儲存格變動方式"來看,應該是觸發事件 04/14 11:09
soyoso: worksheet_change,執行application.calculatefull,不要 04/14 11:09
soyoso: 儲存格變更值就執行重新運算的動作,就寫個判斷來限縮執行 04/14 11:09
soyoso: 動作的範圍 04/14 11:09
在這例子,「事件」可能比 application.volatile 還要差?
限定範圍是在公式寫 if 範圍內有變動 就重算 嗎?這個程式碼應該怎麼寫呢?
另一種方法,我已經把excel公式拆成兩格,那就寫兩個自訂公式,公式搬進VBA就好
至少維護不用擔心公式跑掉,也會自動重算
soyoso: 有限縮觸發事件範圍的話,不會 04/14 14:19
soyoso: 限縮不是寫在公式function內,而是觸發事件內 04/14 14:19
soyoso: 看要range.row、range.column、range.address或是 04/14 14:19
soyoso: intersect 04/14 14:19
我想了一下,在我的情境,這樣寫法跟原本差不多@@現在卡在另一個

Function bcd(X As Range)
XR = X.Row
XC = X.Column
y1 = X * 2
y2 = X * 3
bcd = y1
Cells(XR, XC + 2) = y2

是否無法這樣寫,只能sub然後

Set X = Application.InputBox(prompt:="輸入X的儲存格", Type:=8)

用sub似乎就沒那麼多問題,可是好像只能一個一個做,大量資料就要用陣列?
soyoso: 不要一個一個做的話,也可以迴圈,取出自訂函數bcd括號內 04/15 11:10
soyoso: 的儲存格字串range.formula 04/15 11:10
Range.Formula類似「拉公式」?迴圈我會好好想
waiter337: 我給個特別操作 04/15 15:32
waiter337: Function abc(X As Range) 04/15 15:32
waiter337: Dim XR As Integer, XC As Integer 04/15 15:32
waiter337: XR = X.Row + 2 04/15 15:32
waiter337: XC = X.Column 04/15 15:33
waiter337: abc = Application.Average(Range(Cells(XR - 2, XC), 04/15 15:33
waiter337: Cells(XR, XC))) 04/15 15:33
waiter337: End Function 04/15 15:33
waiter337: 然後 04/15 15:33
waiter337: 儲存格F10 =abc(E8:E10) 04/15 15:34
這個方法確實可行,但我不太懂為何他只有一個range,而且是第一個的range
如果要保留3個range,是否要用陣列?
waiter337: 不過還是給建議 別用這種方法 04/15 15:35
waiter337: 像s大的建議一樣 既然都用vba 就別在儲存格工作表上用 04/15 15:35
waiter337: 自訂函數了 04/15 15:35
waiter337: 其實自訂函數是個很肌肋的功能 04/15 15:36
waiter337: 寫了vba三年多 自訂函數的功能 也只有今天用上而已 04/15 15:37
waiter337: 使用率其實非常低 而且就如同s大所說的 04/15 15:37
waiter337: 你現在會卡死不能變更儲存格規劃好的位置 04/15 15:38
waiter337: 就是因為你用vba 又套 儲存格公式 所才變得礙手礙腳 04/15 15:39
waiter337: 建議直接往純vba的方向靠攏 04/15 15:39
waiter337: 另外這段我自身也有經歷過 04/15 15:40
waiter337: 要改成純vba操作反而很快 yt線上課程看看 一星期就能 04/15 15:40
waiter337: 整個習慣改變成功 並且vba套儲存格函數 很容易出現 04/15 15:41
waiter337: 未知的bug 並且更容易出錯 比如你這次碰上的狀況 04/15 15:41
waiter337: 其實還有3~5種你還沒碰到=,= 我都碰過 04/15 15:42
waiter337: 山不轉路轉 祝你順利 04/15 15:42

因為我的資料滿複雜的,而且格式也還沒確定,自訂函數好處是很好挪,用VBA寫要先規
劃好?我的陣列跟迴圈要想很久,之前寫兩三個都是卡很久才成功運作@@

我公式的x要輸入4個,x1 x2 x3 x4,輸出的y可以有5種,5種y的算式大多相同,少部份
是正負號相反,乘法變除法。之前寫自訂函數,真的就拆成5個公式,y1公式y2公式...
現在是用一個公式,然後多一個x5,x5輸入y1y2...得到對應的y。
有時候5種y都要用到,等於很多運算都是重複的,這就應該寫成sub?寫到一半發現我只
是只是把function從活頁搬進sub而已...計算還是一樣大量重複,如果把原公式輸入進
去,程式碼就會變得很多行,看起來怪怪的,這反而是正常?

這篇格子問題,其實就是不知道怎麼處理這個問題,function可以一次算5種y,可是只
能輸出一個y,sub可以輸出多個,但輸入就不能用拉的,好像要用迴圈?我還沒想通,
放假要好好想想怎麼做。

waiter337: 你匯入的範圍 就屬於觸發的範圍 沒有這樣設定 04/16 16:57
waiter337: 當你操作了其他儲存格 他並不會觸發 04/16 16:57

這個問題是:輸入E8到E10,為何VBA這邊只會保留一個格子,而非三個,而且這個格子
是E8而不是E10或E9。之前我有問另一個很像的,一連串的格子,大於0的有很多個,要
找出最後一個大於0的數值,我弄出來都是第一個,而soyoso的解法,我覺得很訝異,到
現在還是覺得怪怪的,應該有別的方法。

waiter337: 順便回復你的回答 04/16 16:58
waiter337: 這種情況就是美麗的誤會 04/16 16:58
waiter337: 因為就是人會有稟賦效應 04/16 16:59
waiter337: 所以更難看清 未來如果擁有了更新的技術 會發生甚麼事 04/16 16:59
waiter337: 而我們已經完全用vba的人 其實以前也是很喜歡用儲存格 04/16 17:00
waiter337: 但正是因為 當時被儲存格公式虐到過一次大條的 04/16 17:01
waiter337: 所以就靠攏純vba 才發現純vba很好用 04/16 17:01
waiter337: 依照你目前的例子 其實換作用純vba操作的人來判斷 04/16 17:02
waiter337: 反而會覺得你目前的做法 是更複雜更難的 04/16 17:02
waiter337: 反之若一直不嘗試靠攏過來 就會永遠不知道那份感覺 04/16 17:05
waiter337: 不然站內 可以幫你看看怎麼規劃解決 04/16 17:06
waiter337: 如果真的要給條界線 04/16 17:07
waiter337: 大概如下 一個過程 資料>運算>結果 算一階 04/16 17:08
waiter337: 如果你的結果是必須要達到3階以上的狀態才能得到 04/16 17:08
waiter337: 那麼vba才會是好的方向 因為不知道未來還有多遠的運用 04/16 17:09
waiter337: 如果當下只有小範圍1~2階段 那就用公式函數解決 04/16 17:09
waiter337: 另外 儲存格公式的檔案 就整個都用儲存格公式 別用vba 04/16 17:10
waiter337: 反之用vba巨集 就單純用vba巨集 別用儲存格公式 04/16 17:11
waiter337: 這兩者混用 基本上就是衝突的開始 04/16 17:11

簡單的自訂函數,我想還是可以啦,我看過一個老檔案,他一個統計學的公式,寫了一
大串,連Pi=3.14...居然要寫成Const放在最前面。現在excel已經有內建這些公式了

資料最低階的處理,我已經做出來了,用VBA算是節省效能和練習寫程式吧
但是再高階的應用,礙於我的數學程度,還沒想清楚要怎麼弄出來,目前想到的做法,運
算量不小,但最搞笑的是,我不知道這樣計算是否正確,也不知道如何驗算答案...

waiter337: 另外儲存格陣列 跟 vba陣列是不太相同的做法 04/16 17:14
waiter337: 我無法判斷你說的陣列是哪種 但我覺得建議別在這裡用 04/16 17:14
waiter337: 先學vba的一般陣列會比較好 04/16 17:14
waiter337: 最後給你個願景八 如果你開始往vba靠攏 一鍵解決是沒問 04/16 17:17
waiter337: 題的 一個按鈕就搞定這樣 04/16 17:17

目前的規劃:從網路抓csv檔,轉置excel,輸入vba並計算,輸出excel,人工選取需要的
資料並存在excel。是否需要csv直通vba不經過excel呢?

目前我卡在陣列:

Option Base 1

Sub testar2()
Dim i As Integer, j As Integer, ar(5, 4) As Integer
For i = 1 To 5
For j = 1 To 4
ar(i, j) = i * j
Next
Next
Range("A6").Resize(5, 4) = ar

二維陣列沒問題

Sub testar()
Dim i As Integer, ar(5) As Integer
For i = 1 To 5
ar(i) = i ^ 2
Next
Range("A6").Resize(5, 1) = ar
End Sub

一維陣列這樣只會得到5個1,好奇怪

Range("A6").Resize(1, 5) = ar

數值正常,但他是橫的,要如何變成直的?


另外我的陣列輸入這樣寫對嗎?輸入B2:B11

For i = 1 To 10
ar(i) = Range("B" & i + 1)

---

ar = Range("B2:B11")

我本來是這樣寫,但跑不出來...看網路範例都這樣呀?

soyoso: 轉置,worksheetfunction.transpose(ar) 04/17 11:08
soyoso: 要ar = Range("B2:B11")不以迴圈的話 04/17 11:12
soyoso: 宣告dim ar或dim ar as variant 04/17 11:12

用迴圈跟不用,兩者哪個比較好呢?不用迴圈的,就會變成二維陣列?
運算式本來寫 ar(i)=ar(i)*2 變成 ar(i,1)=ar(i,1)*2 不能寫ar=ar*2?

如果輸入100列2欄,輸出3欄,我是把每1欄都寫成1個一維,總共5個
是否寫成輸入陣列(100,2),和輸出陣列(100,3),這樣比較好?
或是直接一個陣列(100,5)就好了?那這個的輸出寫法是
Range("C2").Resize(100,1) = ar(100,3)
Range("D2").Resize(100,1) = ar(100,4)
Range("E2").Resize(100,1) = ar(100,5)
?這三行寫成一行有辦法嗎?或是分成輸入輸出陣列
Range("C2").Resize(100,3) = ar2

soyoso: 我先回原po回文「還有"soyoso的解法,我覺得很訝異,到現 04/17 14:08
soyoso: 在還是覺得怪怪的,應該有別的方法。"」 04/17 14:08
soyoso: 哪個解法?請提出,如果指range.formula,我並沒有回文寫 04/17 14:08
soyoso: 這是拉公式 04/17 14:08
那個例子是這篇 #1WBA_rjh 。拉公式是我的理解
soyoso: 原po回文寫"sub似乎就沒那麼多問題,可是好像只能一個一個 04/17 14:08
soyoso: 做" 04/17 14:08
soyoso: 我寫了"不要一個一個做的話,也可以迴圈,取出自訂函數bcd 04/17 14:08
soyoso: 括號內儲存格字串range.formula" 04/17 14:08
soyoso: 要如何取得儲存格字串,就以range.formula,為什麼要取得 04/17 14:08
soyoso: 這個公式,因為括號內有儲存格字串 04/17 14:08
soyoso: 有這個字串可以幹嘛,就可以迴圈執行Cells(XR, XC + 2) = 04/17 14:08
soyoso: y2這個動作,只不過用的是range 04/17 14:08
soyoso: 接著回12:20:07的回文 04/17 14:08
soyoso: 兩個哪個比較好?以實際資料自行測試就會知道了。 04/17 14:08
我只有簡單測試。本來用一維寫了幾十列,改成二維有點麻煩,就沒直接試。之前在圖
書館看書時,提到 Range("A1").Resize(i,j) = ar 優於
在迴圈內 cells(i,j) 放入陣列值(i,j) (應該是吧?)
但在這問題,是兩三個陣列好,還是一個好,似乎差不多?
soyoso: 要一維的話,一樣轉置,同上回文寫法,改轉置儲存格範圍 04/17 14:08
soyoso: 可以一起寫,用application.index的方式 04/17 14:08
soyoso: 要每欄寫成1個一維或是二維(維度下限大小的不同)就看哪個 04/17 14:08
soyoso: 原po目前所知且是可以達成要的結果,就以該方式達成 04/17 14:08
application.index用法查網路看不太懂@@
如果其他差不多,維度我覺得一欄一個一維打法比較簡單,二維(i,1)跟(i,2)代表哪欄,
需要另外記名字,一維就有自己的名字。
soyoso: 回文"那個例子是這篇 #1WBA_rjh",所以哪裡怪了,函數有函 04/17 17:24
soyoso: 數的特性,怪在哪?又不可能每個函數都相同 04/17 17:24
如果是vba陣列,直覺是用UBound查最後一個
剛剛我試了後,發現卡在如何篩選不要的元素 囧
soyoso: 我還是同04/17 14:08回文"看哪個原po目前所知且是可以達成 04/17 17:24
soyoso: 要的結果,就以該方式達成。" 04/17 17:24
soyoso: 原po覺得一欄一個一維打法比較簡單,且這方面可以理解,又 04/17 17:24
soyoso: 可以達成要的結果,那就以該方式達成;那要問兩三個陣列好 04/17 17:24
soyoso: ,還是一個好,這要看實際資料和實際要執行的動作來測試, 04/17 17:24
soyoso: 有測試才有數據,才能說這二則之間,"差不多"的程度是否是 04/17 17:24
soyoso: 原po可以接受的,畢竟"差不多"本身是因人而異的不是嗎? 04/17 17:24
其實我也不知道怎麼測試,有的速度差異很明顯,這種我想看不出來
剛剛想了一下,如果陣列用迴圈輸出到活頁,比較沒效率,那麼活頁用迴圈輸入到陣列,
應該也不好。那麼一欄一個二維陣列,似乎比較好?因為只有二維陣列可以一次輸入
soyoso: 篩選最後一筆符合的話,迴圈反序step 負數,判斷,符合時跳 04/17 20:24
soyoso: 出迴圈 04/17 20:24

居然這麼簡單!!!如果要篩選特定元素應該怎麼寫呢?

Option Base 1

Dim ar, br
ar = Range("A1:A10")(數值1到10)
For i = 1 To 10
If ar(i, 1) > 5 Then
br = ar(i, 1)
End If
Next

比如說br應該有5個元素,上面那樣寫,br是10,而br(i,1)跑不出來,若寫成
redim br(10,1)
br(i, 1) = ar(i, 1)
則會有5個「空格」,要如何讓這些空格消掉?使br只有5個元素

soyoso: 測試上可提供實際的資料檔案和說明實際要執行的動作 04/17 20:27
soyoso: 效率上是回文寫到的一次輸入比較好 04/17 20:38
soyoso: br,redim一維,二維的話br(1,10),判斷內設個變數累加, 04/17 22:17
soyoso: 變數=變數+1,br(變數)/br(1,變數)=ar(i,1),迴圈結束後 04/17 22:17
soyoso: 再redim preserve,陣列大小就以變數 04/17 22:17
br(1,10)反過來寫成br(10,1)就卡住,為什麼呀?變數的方法真的很酷

Dim ar, br, count As Integer
ReDim br(10)
count = 0
ar = Range("A1:A10")
For i = 1 To 10
If ar(i, 1) > 5 Then
count = count + 1
br(count) = ar(i, 1)
End If
Next
ReDim Preserve br(count)

但如果刪除第二行的redim,第一行改為dim br(10),為什麼就會卡住呢?
我覺得陣列這部份最難搞懂,搞不清楚他的規則,每次不知道為什麼卡住@@
soyoso: 這方面查redim,註解內都有寫 04/18 11:24
soyoso: ReDim語句是用來大小或重設已正式宣告的動態陣列...或Dim* 04/18 11:24
soyoso: * 語句 (不含維度下標) 04/18 11:24
soyoso: 如果您使用Preserve關鍵字, 您只能調整最後一個陣列維度的 04/18 11:24
soyoso: 大小, 而且您無法變更所有維度的數目。 04/18 11:24
用Debug.Print IsArray(br)看,dim br()有括號是陣列,沒括號就不是
但如果dim括號有數字,則無法用redim,是這樣嗎?這讓我想到
Dim quantity As Integer = 10 這種寫法,官網有這個範例,但我的vba跑不出來
只能 Dim quantity As Integer 然後 quantity =10
redim是這種關係,但用於陣列?
soyoso: 回文寫了"不含維度下標",原po測試就知道有數字,redim可 04/18 12:42
soyoso: 否使了不是嗎? 04/18 12:42
soyoso: ^用 04/18 12:42
剛剛我大概把(不含維度下標)想成別的東西
soyoso: Dim quantity As Integer = 10 這種寫法 04/18 12:45
soyoso: 請看 https://i.imgur.com/OncnrnJ.jpeg 上面不就寫了VB, 04/18 12:45
soyoso: 並沒有寫vba啊,有些通用,但不表示vba內就可以使用好嗎 04/18 12:45
以後我會注意這種差異了@@
soyoso: 應以這個才是 https://i.imgur.com/zpdHwUB.jpeg 04/18 13:03
waiter337: 為什麼redim刪除會卡住 04/19 16:48
waiter337: 不用告訴你原因 你直接開個新sub 04/19 16:48
waiter337: 然後用 f8 去執行 然後新增監看式br 04/19 16:49
waiter337: 看看會發生甚麼事情 就明白了 我反而會說的你很亂 04/19 16:49
waiter337: Sub test() 04/19 16:52
waiter337: Dim ar 04/19 16:52
waiter337: ReDim ar(3) 04/19 16:52
waiter337: ReDim ar(2, 1) 04/19 16:52
waiter337: ar(0, 0) = 123 04/19 16:52
waiter337: ReDim ar(2, 1) 04/19 16:52
waiter337: ar(0, 0) = 123 04/19 16:52
waiter337: ReDim Preserve ar(2, 1) 04/19 16:52
waiter337: ReDim Preserve ar(2, 2) 04/19 16:53
waiter337: ReDim ar(2, 3) 04/19 16:53
waiter337: End Sub 04/19 16:53
waiter337: 一個個看有甚麼變化就懂了,要新增監看把 田ar 展開 04/19 16:54
waiter337: 看看 格子的數量 階層 內容 有甚麼變化 04/19 16:55
waiter337: 初學陣列基本上就跟工作表擺放格子一樣 不用想的太麻煩 04/19 16:56
waiter337: 除非未來有機會碰到3維在繼續進一步思考 04/19 16:56
waiter337: 或者多維 04/19 16:57
waiter337: 工作表是他EXCEL預設好了格子 04/19 17:43
waiter337: 而陣列就是你要多少格子 你自己擺 04/19 17:43
waiter337: redim 基本上就是全部清空重來 所以要怎麼改都可以 04/19 17:45
waiter337: 改多改少改寬改窄都可以 04/19 17:45
waiter337: 但如果用上preserve 就會保留原始資料 只能多不能少 04/19 17:46
waiter337: 雖然說是成功保留原始資料 但也是清空重刷過後了唷 04/19 17:47
waiter337: 但因為有資料 所以你不能改小 04/19 17:47
waiter337: 如果是一開始學 可以只練習用redim 一次開好就好 04/19 17:49
waiter337: 盡量不碰保留 反正久了就會了 04/19 17:50
waiter337: 補充 如果資料量龐大 用了preserve 很容易會變慢 04/19 17:50
何時會用redim更改陣列維度呢?感覺用兩個陣列來處理比較簡單吧?
應該說redim preserve的刪除只能是最後一維,這點有點討厭,在上面的案例,在二維就
出現了@@ 沒用過二維以上的,變慢是因為要從前面的維度一個一個進出,然後增減最
後一維度?有點像用迴圈存取活頁?
waiter337: 最後一句沒解釋清楚 用迴圈一直觸發preserve 會變慢 04/20 16:14
waiter337: 關於為何要用二維陣列這個問題 04/20 16:15
waiter337: 在於必須先了解數據的基本組成概念 04/20 16:15
waiter337: 但白話的說 04/20 16:16
waiter337: 就是如果今天你的單筆資料 就有十個屬性 04/20 16:16
waiter337: 比如 姓名 電話 地址 日期 新增人 備註 手機 email 04/20 16:17
waiter337: 那麼 你就得創很多個一維陣列 04/20 16:17
waiter337: 但如果用2維陣列 你只要打個數字 就能一次創好 04/20 16:18
waiter337: 不過這個問題很好 一維陣列 跟二維陣列 使用時機 04/20 16:18
waiter337: 並沒有很侷限 你可以依照自己的習慣 或者學習經驗 04/20 16:19
waiter337: 慢慢嘗試 找到你最喜歡的寫法 04/20 16:19
waiter337: 另外preserve變慢的原因是 是舊的資料要轉移到新的陣列 04/20 16:21
1000列10個屬性,用10個一維(1000)和1個二維(1000,10),差異是什麼呢?不過在命名
上,我想10個比較好,因為(i,7)屬性是什麼?還要去查一下。但是一維不能一次從活
頁輸入資料,所以變成二維(1000,1)。那麼10個二維(1000,1)和1個二維(1000,10)哪個
好?如果沒差,我覺得10個比較好,至少名字很清楚。
redim preserve 我大概只用在前面刪空格的問題,如果本質是舊陣列搬到新陣列,而
我只是輸出到活頁,那麼更簡潔的寫法,應該是不用刪除空格,只輸出前面的元素就好
--
後來我想到,10個屬性從活頁搬進10個二維,那麼就要做10次,而1個二維只要1次,輸
出也一樣。如果真的很多,我想10個可能要減少成2~4個,1個我覺得除非都做好了,最
後再來修成這個版本吧,不適合邊寫邊改。
waiter337: 沒有好不好 只有習不習慣的問題 主要是看資料的分佈狀 04/20 22:47
waiter337: 況 這麼說好了 04/20 22:47
waiter337: 只用一維陣列 總有天會碰到要用二維的方式 04/20 22:47
waiter337: 而相反 只用二維 總有天也會需要碰到一維 沒有好不好 04/20 22:47
waiter337: 只有適不適合 04/20 22:47
waiter337: 比如你說的要設定名稱的概念 04/20 22:47
waiter337: 就跟你有10個員工 但你也可以用編號給予編號 這個沒有 04/20 22:47
waiter337: 任何問題 04/20 22:47
waiter337: 但如果有1000個員工呢 就肯定會用上編號 依照目前你的 04/20 22:47
waiter337: 狀況 就算用編號 也不會造成出錯 就能用編號 反之就設 04/20 22:47
waiter337: 定名稱 甚至 一部分編號 一部分名稱 都是可以的 04/20 22:47
並非座號這種,而是有名字的屬性變成數字流水號 (1,2)=43 (1,3)=65 (1,4)=87
這三個屬性有時間、高度、重量,你覺得哪個編號是哪個屬性?對我來說,那樣的程式
碼真的不會想看第二次,最多只能都做好了,不會再改了,才能改成這樣。
waiter337: 另外問 什麼是刪空格? 如果你只要6-10列 04/20 23:14
waiter337: 你只要redim ar(6 to 10) 04/20 23:14
waiter337: 這樣就不用擔心還要加減調整位置去符合儲存格欄列號 04/20 23:15
保留資料,刪除沒有資料的索引,比如ar5個索引(空,2,4,8,空),我只想留(2,4,8)
ReDim Preserve ar(1 To 4) 可以跑
ReDim Preserve ar(2 To 4) 不行
而 ReDim ar(2 To 4) 會變成3個索引的空陣列,索引沒有0和1
我應該用不太到這種,而且感覺很難用@@應該只會用上面篩選那邊的方法
ReDim br(10)
ar = Range("A1:A10")
For i = 1 To 10
If ar(i, 1) > 5 Then
count = count + 1
br(count) = ar(i, 1)
End If
Next
ReDim Preserve br(count)
waiter337: 1.的回答 有種東西叫做"註解" 04/21 19:07
不論是'註解,或螢幕旁邊貼便條,我還是不太喜歡這種寫法,也許是資料類型不同
waiter337: 第二段 因為不是這樣用 04/21 19:07
waiter337: 1 to 4 是針對 讓儲存格跟陣列能夠保持同欄列號用的 04/21 19:09
waiter337: dim ar 04/21 19:11
waiter337: redim ar(1 to 10) 04/21 19:12
waiter337: for i = 1 to 10 04/21 19:12
waiter337: ar(i) = cells(i,1) 04/21 19:12
waiter337: next 04/21 19:12
waiter337: 更正一下好了 04/21 19:13
waiter337: dim ar 04/21 19:13
waiter337: redim ar(1 to 10) 04/21 19:13
waiter337: for i = 1 to 10 04/21 19:13
waiter337: 打錯了 更正一下好了 04/21 19:14
waiter337: dim ar 04/21 19:14
waiter337: redim ar(1 to 10) :w=1 04/21 19:14
waiter337: for i = 1 to 10 04/21 19:15
waiter337: if cells(i,1)>5 then ar(w)=cells(i,1):w=w+1 04/21 19:15
waiter337: next i 04/21 19:15
waiter337: end sub 04/21 19:15
waiter337: 跟你的意思一樣 這樣才是為什麼用 1 to 10 的原因 04/21 19:16
用迴圈一個一個輸入,這寫法不好,我覺得不需要活頁列號跟陣列位置相同
waiter337: 還有一個概念 陣列盡量在可行的狀況下 設越多越好 04/21 19:22
waiter337: 不用省 主要因素是 當你真的有空去省的情況 04/21 19:22
waiter337: 1.你程式不省記憶體絕對不夠用 只能省 04/21 19:22
waiter337: 2.已經能完美運行了 優化他的狀況 04/21 19:23
waiter337: 更多的問題並不是浪費記憶體資源 而是當初開得不夠用 04/21 19:23
waiter337: 為了後者遇到的狀況而提早杞人憂天 反而會影響你寫程序 04/21 19:24
waiter337: 的練習與昇華 因為如果陣列很強的人 在還沒開始寫之前 04/21 19:24
waiter337: 都已經能直接預判從頭到尾要耗費的陣列大小了 04/21 19:25
waiter337: 所以對於陣列用上癮的 通常不會有這個問題 04/21 19:25
waiter337: 盡量開八 印象是至少有30萬格起跳 04/21 19:26
waiter337: 最高好像有到幾百萬格 04/21 19:27
waiter337: 這個概念就像 你優化10秒到1秒 是很有效率的 04/21 19:27
waiter337: 但如果陣列的速度 從0.01秒優化到0.001秒其實影響甚微 04/21 19:28
我的資料沒有這麼多,但是效能真的滿有感的,我第一個sub真的很慢,超過十秒,現在
不到一秒。首先是數學上大量重複計算,再來程式寫得不好。用手算就會知道哪邊是重
複的,直接抄過來就好,電腦只會一直重複計算。會這樣是因為程式比較好寫又簡潔,
寫fuction只有一行,若要提昇效率,改成會記憶的變數,就好幾十行。雖然說寫程式之
前要規劃,實際是邊寫邊改,更何況新手我一直卡在奇怪的地方,不然就是不知道為什
麼跑出來是錯的。總之我差不多寫完一個簡單實用的sub,雖然結構只是大的for迴圈,
內部一個do迴圈,好幾個if。但這些不是一次寫完,而是修修改改,圖書館翻書,來這
個板求救,這樣子才成功搞定。當中我覺得,陣列跟for迴圈結合,這個技巧真的是最重
要的。
waiter337: 回一個部分 你說用迴圈一個一個輸入不好 04/21 22:55
waiter337: 肯定是你誤會了甚麼 04/21 22:55
waiter337: 因為有地方你遺漏了 04/21 22:56
waiter337: 如果 你從儲存格上一個一個匯入陣列 其實他分成兩種 04/21 22:57
waiter337: 操作 04/21 22:57
waiter337: 1.找到工作表>找到儲存格位置>寫入陣列 04/21 22:58
waiter337: 如果使用二種方法 04/21 22:58
waiter337: 我直接set 工作表 到記憶體 04/21 22:58
waiter337: 比如原先是sheets("工作表1").cells(i,1) 04/21 22:59
waiter337: 而我們讓他變成 04/21 22:59
waiter337: set s= sheets("工作表1") 04/21 22:59
waiter337: s.cells(i,1) 04/21 22:59
waiter337: 那麼 這樣的概念就是 表已經在記憶體內了 04/21 23:00
waiter337: 只要找位置>匯入陣列而已 就不會慢 04/21 23:00
waiter337: 意思就跟你會先 ar=range("a1:a10") 完全是一樣的概念 04/21 23:00
set物件這種我倒沒用過,試了一下馬上就卡住@@
s.Cells(1, 1).Value = 123 不能這樣寫嗎?我再翻書看看
waiter337: 迴圈其實非常快 曼的不是迴圈 而是你用迴圈不小心做了 04/21 23:01
waiter337: 看不見的多於底層程序觸發到一些奇怪的呼叫與引用 04/21 23:01
waiter337: 其實目前你的狀況要多嘗試不同做法 04/21 23:03
waiter337: 實際狀況是這樣 從copy到會用陣列 會快很多 04/21 23:03
waiter337: 但 從陣列到達 3維陣列 又會快更多 04/21 23:04
waiter337: 而當中必定要經過2維陣列的學習 04/21 23:04
waiter337: 這樣說好了 我有個檔案原本預計要跑40分鐘 3萬筆 04/21 23:04
waiter337: 現在用到一般陣列大概50秒 3維陣列6秒 04/21 23:05
waiter337: 而且我在此篇講的所有技巧全部都得用到 04/21 23:06
waiter337: 祝你未來成為高手! 04/21 23:06
waiter337: 關於註解的問題 04/21 23:11
waiter337: 三維陣列就是一個 完全依照數字存取的概念 04/21 23:11
waiter337: 若無法先學會二維陣列 那麼三維陣列的學習勢必會遇到 04/21 23:12
waiter337: 阻礙 請盡量的多方嘗試與練習 04/21 23:12
三維我還沒想通怎麼用,二維就一個活頁的欄列,第三維就是不同活頁?
waiter337: 比如 擬利用encode的方式找出文字開頭作強制分類 04/21 23:13
waiter337: 那麼分出來的資料就會從48~90 或者找尾數0~9 04/21 23:15
waiter337: 直接利用數字放入各各陣列中的陣列 04/21 23:16
waiter337: 然後需要直接依編號提取 就會用上這種方式 04/21 23:16
encode 是 WorksheetFunction.EncodeUrl 這個嗎?是處理網址用的?
waiter337: 另外可以搜尋這篇 知道如何將陣列資料匯出 04/21 23:16
waiter337: .DB6.html 請合併網址 04/21 23:17
waiter337: 抱歉 多個. 04/21 23:17
waiter337: #1OYh_fss (Visual_Basic) 04/21 23:18
waiter337: 之前你抓的那個檔案 裡面有大概教如何使用 04/22 19:44
waiter337: encode 更正一下 我打錯了 是asc 才對 04/22 19:47
是 ASC() 這個嗎?我還是不知道幹嘛用的@@
waiter337: 三維或者多維的概念不好理解 04/22 19:49
waiter337: 你的講法沒錯 只要是有大範圍 中範圍 小範圍都能解釋 04/22 19:49
waiter337: 有人也會以 軍隊分配 或者 公司規模 或者 縣市地區 04/22 19:51
waiter337: 這種 大中小 的方式作為概念 04/22 19:51
waiter337: 但說白了 就是將二維的概念 延伸 04/22 19:51
waiter337: 這種概念認知方式 我的建議是 每種都拿來測看看 大腦 04/22 19:52
waiter337: 偏好喜歡哪種認知方式 對了 還有一種 直線/平面/方塊 04/22 19:52
waiter337: 或者你去搜尋這個三字 04/22 19:53
waiter337: vector matrix array 看能不能找google找圖 04/22 19:53
waiter337: 還有一個data frames 04/22 19:54
waiter337: 但雖然三維說得很厲害一樣 但實際寫程序時 也不過就3 04/22 19:58
waiter337: 組數字而已 所以要去試著擴散大腦連結這兩種概念 04/22 19:59
waiter337: 前提先練習二維 轉一維 或者一維轉二維 三維會比較好練 04/22 20:00
waiter337: 因為陣列的用意 就是把很複雜的資料 用數字編號整理好 04/22 20:08
waiter337: 方便運用 04/22 20:08
waiter337: 就跟你把工作表開20個 照編號1~20 04/23 05:50
waiter337: 然後裡面的列號也是1~20 04/23 05:50
waiter337: 欄號也是1~20 04/23 05:50
waiter337: 那麼就有8000個位置 04/23 05:51
waiter337: 假如我要第15個工作表的 2列10號 那麼就是ar(15,2,10) 04/23 05:51
waiter337: 忘了補充上述情景,假設所有陣列都從1開始的情況 04/23 05:52
我的資料是有機會用到三維,但因為資料特性,我還無法寫出簡單的程式
再慢慢想啦,有機會再跟你請教~
waiter337: asc()可以把文字轉成數字編號 04/24 19:43
waiter337: 剛好可以搭配陣列運用 就能減少搜尋範圍或著直接對照 04/24 19:43
waiter337: 編號擺入 甚至用到三維或四維 04/24 19:43
a=97 y=121 所以編號a-y-3-67 陣列就是(97,121,3,67)?
waiter337: 說個題外話 屬個人主觀 可以不必強制自己接受 04/24 19:54
waiter337: 純vba為什麼會讓我完全幾乎放棄函數公式的原因 04/24 19:54
waiter337: 1.可以f8 不用一次寫的自己都看不懂 只有start 跟 end 04/24 19:54
waiter337: 無法快速判斷自己是否誤寫 04/24 19:54
waiter337: 2.延伸與通用性 當開始擁有了一個output結果 未來會有 04/24 19:54
waiter337: 極大的機率必須要再次利用這個結果 vba甚至可以寫到10 04/24 19:54
waiter337: 幾階的運用 04/24 19:54
waiter337: 3.userform可以運用 04/24 19:54
waiter337: 4.可以快速改版迭代 保留原始資料 不用擔心牽一髮動全 04/24 19:54
waiter337: 身 尤其是一個已經 經過多層階段的結果運用 04/24 19:54
waiter337: 4.陣列速度快 04/24 19:54
waiter337: 5.不用擔心不小心去動到工作表而影響全部資料 04/24 19:54
waiter337: 6.引用外部資料方便 04/24 19:54
waiter337: 7.爬蟲 04/24 19:54
waiter337: 8.可以依照框架與經驗 學習更多類型的程式語言 04/24 19:54
waiter337: 9.解決有些公式難以解決的問題的效率 04/24 19:54
waiter337: 10.可以無腦縮短成一個按鍵 04/24 19:54
waiter337: 11.可以運用工作表註解(不是vba註解) 04/24 19:54
waiter337: 12.大多人無法輕易理解 被人竄改資料 04/24 19:54
waiter337: 基於這些 也就是我推薦你靠攏純vba的建議 04/24 19:54
waiter337: 甚至有些一定要背的函數公式套路 可以繞過 直接用陣列 04/24 19:57
waiter337: 迴圈的基本操作給處理掉 04/24 19:57
背公式如果能解決多數難題,那也不太壞,問題是好像沒什麼書整理這些東西,無從背
起,不然就是看不懂範例是幹嘛的?下次遇到還是不知道怎麼做。
我正在寫另外一個sub,輸入只有2欄,要做判斷,輸出一樣是2欄,我一直都是用手工做
這些。寫出來只是好幾個if,但是推倒重寫很多次,才成功跑出正確的東西。這次寫的
技術不難,但人腦邏輯怎麼化成程式邏輯很重要,好幾個if,誰在外面,誰在裡面,或
是獨立,跑出來的東西都不一樣,而且常常跟我預期的不一樣@@人腦算到一半,發現
怪怪的,可以退回重算,程式似乎很難這樣寫。
waiter337: if 有2種高級(?)寫法用法 可以講判斷在工作表列出 04/25 21:14
waiter337: 來 然後拆解 就可以完全避免巢狀 至少可以不用用到三 04/25 21:14
waiter337: 巢狀 04/25 21:14
waiter337: 天晴 吃飯 睡覺 睡覺 不要訂鬧鐘 要戴眼罩 04/25 21:19
waiter337: 雨天 吃菜 唱歌 睡覺 睡覺要訂鬧鐘 如果星期一 要7點 04/25 21:19
waiter337: 星期二8點 04/25 21:19
waiter337: 其他日9點 04/25 21:19
waiter337: 很多人的寫法 大部分會 一個包一個 巢下去 04/25 21:21
waiter337: 其實大可不必 全部拆開 直接搭配and就好 04/25 21:22
waiter337: 但許多人會說 這樣不是浪費效能嗎 04/25 21:25
waiter337: 是的 但真的要效能時再包就好 04/25 21:25
waiter337: 而且 工作表上已經有藍圖了 直接複製到vba裡面當註解 04/25 21:25
waiter337: 參考 04/25 21:25
waiter337: 然後 04/25 21:25
waiter337: 有些太吃運算並且重複使用的的功能 就把它提前在if前 04/25 21:25
waiter337: 設好變數 之後就能直接用 04/25 21:25
waiter337: 1.天晴+吃飯+睡覺+不要訂鬧鐘+要戴眼罩 04/25 21:27
waiter337: 雨天 吃菜 唱歌 睡覺 睡覺要訂鬧鐘 如果星期一 要7點 04/25 21:27
waiter337: 對不起 更正 04/25 21:27
waiter337: 重來 04/25 21:27
waiter337: 1.天晴+吃飯 04/25 21:28
waiter337: 2.天晴+睡覺戴眼罩+不要訂鬧鐘 04/25 21:28
waiter337: 3.雨天+吃菜 04/25 21:28
waiter337: 3雨天+唱歌 04/25 21:29
waiter337: 5雨天+睡覺+訂鬧鐘+星期一7點 04/25 21:30
waiter337: 6.雨天+睡覺+訂鬧鐘+星期二8點 04/25 21:30
waiter337: 6.雨天+睡覺+訂鬧鐘+其他9點 04/25 21:30
waiter337: 排序我忘了改 你改一下1-7就對了 04/25 21:31
waiter337: 這樣是不是簡單易懂 一層就能搞定 04/25 21:31
waiter337: 雖然有點小錯 但大致上是這個意思 04/26 01:42
waiter337: https://i.imgur.com/a/c6o7JG1.jpg 04/26 01:42
waiter337: 有點反直覺 但很好用 下面應該是elseif 我忘了改 04/26 01:43
列舉法,大概只能用在這種簡單有限的情境
我的是要找出突出(異常)的數值,初步直覺是只有一個if,不就正常/異常兩種?但是
我的資料要判斷沒這麼簡單,這個隱含在內的邏輯至少要兩個if,2^2=4種結果,若是三
個if,2^3=8種結果,要記錄1種結果就要1個一維陣列。雖然部份結果是重複的,變數就
不用這麼多,但我還是只能把部份人腦邏輯寫出來,剩下的再慢慢想怎麼弄。
我用巢狀IF,有部份結果相同,有沒有辦法省略?
1號IF結果:a運算/b運算/c運算
2號IF結果:d運算/e運算/c運算
c運算的部份能省略為 call sub.c運算 嗎?
但是應該要有資料放進去,這部份是放在陣列,我只用過call function()
call sub 資料會放進去嗎?我還沒測試
waiter337: call的方式很好 function也可以利用 04/26 13:51
但是兩個sub之間,要怎麼交流變數?尤其是陣列的內容
waiter337: 還有一個方式 有的時候可以用if一行式 先過濾一些 04/26 13:52
waiter337: if x=? then [a1]=1 :[a2]=2 :exit sub 這樣 04/26 13:53
waiter337: 甚至規律 或者類型很像時 還可以直接用select case 04/26 13:55
select case是否只能用在有範圍的數值,和有限的情境?
waiter337: 我猜你要的可能是 射線法 你去找一下看看 04/26 13:58
射線法應該用不到,VBA感覺不好寫
後來想到goto這個寫法,有人說這個寫法不好,你怎麼看呢?不過我目前只想用於重複
的段落而已,用fuction和sub還是卡在怎麼傳陣列@@
waiter337: 有兩種方式 可以將變數帶出去 04/27 18:09
waiter337: 1種是 變數本身就在外面也就是把dim ar移道sub xxx()之 04/27 18:09
waiter337: 外的上方 第二種則是call xxx(ar) 就能帶去sub xxx() 04/27 18:10
waiter337: 的裡面 04/27 18:10
waiter337: 最後更正 就能帶去sub xxx(ar)裡面 04/27 18:11
方法1感覺不太好,弄了老半天才跑起來,然後我發現他sub裡面應該要有dim或redim,
這樣才會歸零,然後不知道為什麼這樣就卡住了,而且我這還會執行別的sub,本來想說
是同名的緣故?結果改名字,關掉重開還是卡,後來寫在空白活頁才正常
方法2無法執行,是少了什麼嗎?

Sub ccc()
ar = [A1:B10].Value
Call ddd(ar)
[D1].Resize(count, 1) = Application.Transpose(br)
End Sub

Sub ddd()
For i = 1 To 10
If ar(i, 2) > 0 Then
count = count + 1
br(count) = ar(i, 1)
End If
Next
End Sub
waiter337: sub ddd() 要改成sub ddd(ar) 04/29 00:30
waiter337: 但你沒有把br傳回去不行 04/29 00:31
waiter337: 我都是用偷懶的方法拉 04/29 00:34
waiter337: Dim ar, br, count 04/29 00:34
waiter337: Sub ccc() 04/29 00:35
waiter337: ar = [A1:B10].Value 04/29 00:35
waiter337: Call ddd 04/29 00:35
waiter337: [D1].Resize(count, 1) = Application.Transpose(br) 04/29 00:35
waiter337: End Sub 04/29 00:36
waiter337: Sub ddd() 04/29 00:36
waiter337: ReDim br(UBound(ar)) 04/29 00:36
waiter337: For i = 1 To 10 04/29 00:36
waiter337: If ar(i, 2) > 0 Then 04/29 00:36
waiter337: count = count + 1 04/29 00:36
waiter337: br(count) = ar(i, 1) 04/29 00:36
waiter337: End If 04/29 00:36
waiter337: Next 04/29 00:36
waiter337: End Sub 04/29 00:37

測試了後,外面有dim redim的,裡面應該也要補,變數也要補,不然不會歸零,難怪超
出陣列索引。我不太喜歡這種方法,也許等到程式很大再來用吧?小程式就先輸出到活
頁,再來做第二次的sub。
goto寫法滿方便的,但有人說不好,不知道好不好呢?我有個do迴圈,判斷式會用到do
後的結果,可是第一次需要先給這個結果,所以我把do迴圈內算式複製到前面,看了有
點討厭,因為兩者只差兩三行,其他都是一樣的。如果用goto,就可以直接進do迴圈的
中間。還有個gosub return的寫法,這個寫法比較符合我對程式的想像,也成功解決我
這個問題

...
GoSub line001
...
Exit Sub

line001:
...
Return

line002:
...
Return

End Sub

waiter337: 其實應該不會很複雜 05/01 08:00
waiter337: Sub a() 05/01 08:02
waiter337: x = 1: y = 2: Call b(x, y) 05/01 08:03
waiter337: Z = x + y 05/01 08:03
waiter337: Debug.Print Z 05/01 08:03
waiter337: End Sub 05/01 08:03
waiter337: Function b(b1, b2) 05/01 08:03
waiter337: b1 = b1 * 2 05/01 08:03
waiter337: b2 = b2 * 2 05/01 08:03
waiter337: End Function 05/01 08:03
waiter337: 當然上面不是正規寫法 是預設就是會返回資料(?) 05/01 08:04
waiter337: 正規寫法是Function b(b1, b2) 要改成 05/01 08:04
waiter337: Function b(ByRef b1,ByRef b2) 05/01 08:05
waiter337: 這一定是會強制回傳資料(?)的唷 05/01 08:05
waiter337: 關於回傳返回資料的部分我打個問號 是因為原理有其他 05/01 08:06
waiter337: 原因 05/01 08:06
waiter337: 建議直接去youtu 查傳值跟傳址的差別 05/01 08:07
waiter337: 很多人用門牌跟房子來解釋 05/01 08:09
waiter337: 我用另一個講法 05/01 08:09
waiter337: 你在youtube發現一部很好看的影片 05/01 08:09
waiter337: 你把他的網址傳給任何人 突然某個人又將資料傳給你 05/01 08:10
waiter337: 對不起 更正 05/01 08:10
waiter337: 你把他的網址傳給任何人 突然某個人又將網址傳給你 05/01 08:10
waiter337: 不行 我例子頗爛 05/01 08:12
waiter337: 還是用門牌號 跟 房子 的例子比較好 05/01 08:13
waiter337: 感覺還是挺模糊的 05/01 08:22
waiter337: google 傳值 傳址 門牌 房子 大概看2~3個網站就能 05/01 08:23
waiter337: 反正 傳值就回不去了 05/01 08:25
waiter337: 你也可以改成Function b(ByVal b1, ByVal b2) 05/01 08:25
waiter337: 看看Z會變成多少 05/01 08:25
waiter337: 傳址 是本體根本沒出去過 分身出去了!影分身之術 05/01 08:26
waiter337: byval 是 by value的縮寫 by ref 是reference (參考) 05/01 08:28

傳值、傳參考,我之前搞不清楚,現在我這樣理解:
X=10:Y=20
X、Y叫變數,一個變數等於是一個籃子(記憶體的一個單位?),兩個籃子的標籤分別
是X和Y,內容物則分別是10和20。
VBA預設是傳參考,等於說各個sub、function在計算的時候,是傳遞X、Y這種標籤,找
到籃子後,再來讀取裡面的內容、計算、更改。
比如倉庫紅色籃子是3瓶果汁,黃色籃子是10瓶果汁,員工的任務是把2瓶果汁放進紅色
籃子,那麼他應該是無中生有變出2瓶果汁,然後放進紅色籃子。這過程並沒有摸到黃色
籃子,2瓶果汁也不是從黃色籃子拿出來的。這樣嗎?
傳值不知哪邊用得到?或者其實function本身就是傳值?如果sub的參數都是傳值,那麼
就跟function差不多了?但是要弄個變數去儲存他的答案?
end sub,會消滅這個sub的籃子,除非sub外面有籃子,而且標籤要一樣,資料才會留下
來,但是傳值就不會改動籃子內的東西了。
在前面我的問題中,兩個sub是end了,但外面的籃子(陣列和變數)還在,裡面資料也
還在,所以重新計算時,就會用到這些舊資料,而非原先預期的「空」,所以要補上dim
或redim把籃子清空。
※ 編輯: j2708180 (36.239.159.74 臺灣), 05/01/2021 12:00:53
waiter337: 小時候用過遊戲修改大師 05/01 20:08
waiter337: 如果他傳出來的是值 你怎麼改 hp mp都不會變 05/01 20:09
waiter337: 如果他傳出來的是址 你一改完 就會變 05/01 20:09
waiter337: 就用 數值 跟 地址(路徑) 來解釋 最洽當 05/01 20:10
waiter337: 數值(物質) 地址(路徑) 05/01 20:11
waiter337: 預設是傳址 05/01 20:17
waiter337: 原本的function 記得沒錯有個功能能決定是否會刷新 05/01 20:18
waiter337: 那個部分可能是事件觸發>結束 只要程式跑完 會自動清空 05/01 20:19
waiter337: 除非你像我前面把dim寫在外面 那麼這個項目就不會清空 05/01 20:20
waiter337: 抱歉 更正 那個function的觸發方式 我也不知道是甚麼 05/01 20:23
waiter337: 我只知道 你給定範圍的資料有變化 他就會變 範圍外不管 05/01 20:24
waiter337: 好像有個excel有個功能是控制刷新的 05/01 20:24
waiter337: function 分兩個部分 傳傳值址的預設 跟資料的預設 05/01 20:26
waiter337: 如果是資料的預設 05/01 20:26
waiter337: 如下 05/01 20:34
waiter337: Sub a1() 05/01 20:34
waiter337: x = 1: y = 2 05/01 20:34
waiter337: Call c(x, y) '改成callc(x) 試試 05/01 20:35
waiter337: Z = x + y 05/01 20:35
waiter337: Debug.Print Z 05/01 20:35
waiter337: End Sub 05/01 20:35
waiter337: Function c(b1, Optional ByVal b2 As Integer = 9) 05/01 20:36
waiter337: b1 = b1 * 2 05/01 20:36
waiter337: b2 = b2 * 2 05/01 20:36
waiter337: End Function 05/01 20:36
waiter337: 當b2沒東西時 就自動將b2設成9 05/01 20:39
總之傳值不會改變原變數的值,傳參考會,可是除了x=x+1這種,兩個好像沒差?
那麼什麼情況會需要把ByVal打出來呢?
※ 編輯: j2708180 (218.173.181.14 臺灣), 05/02/2021 13:25:14
waiter337: 這個考倒我了 05/02 13:43

你可能也想看看

搜尋相關網站