How not to optimize in Visual Basic
Optimizing Visual Basic 6.0 code can be fun or tedious, depending on the way you look at it. Here are some pitfalls to avoid when optimizing.
Just remember, this article shows how not to program.
Let's start with a pitfall we fell into.
For i = LBound(arr) To UBound(arr) Total = Total + arr(i) Next i
Does the above code look unoptimized? Shouldn't you rewrite it like this:
Dim LB As Long, UB As Long LB = LBound(arr) UB = UBound(arr) For i = LB To UB Total = Total + arr(i) Next
There is no difference. Optimizing what's displayed in red isn't going to help you much. The start and final values of a For statement are evaluated only once, at the start of the For loop. They are not evaluated at each loop iteration.
What is more, leaving out the i after Next doesn't help. You can leave it, you can remove it, but you can't optimize it.
When you put an If..Then statement on one line, you gain speed, right?
If condition Then statement
Not true. Using the multiline variant is as fast - but often more readable.
If condition Then statement End If
OK. How about the conditions then? Assume that i is a non-negative integer. It can be 0, 1, 2 etc. but not below zero. Then, assume you want to test if i contains a positive number.
Which one would you use to test for that:
Unoptimal string optimization
Case-insensitive StrComp is for sorting, not for testing
You might think that StrComp(,, vbTextCompare) would be an ideal way to handle case-insensitive comparison. It is not, however, because this way you're subject to bugs. StrComp with vbTextCompare (or Option Compare Text) does more than just case-insensitive compare. Strings that don't match literally may compare equal. For example, ae matches the ligature æ. Depending on what you want, this may be desired or undesired in your application. But it isn't pure case-insensitive compare.
Also beware than StrComp(,, vbTextCompare) may work differently under different locales (regional settings). Your program might fail under a locale you haven't tested in.
StrComp is best left for sorting. It's not the best function to compare for equality.
The Like operator looks handy - and it is. Unfortunately it's slow too. Avoid it if you can. Use your imagination with the other string functions, including AscW, Left$, Len etc.
Replace$ does no better than Replace
Replace$ is exactly the same as Replace. There is no string vs. variant difference. No need to add the dollar.
Did you think all byte functions are fast as lightning? Not InputB$. If you need to load in a large file, try some other way.
Data types, objects, variables, arrays
Don't Dim .. As New
Dim obj As MyClass Set obj = New MyClass
Why write 2 lines when you can just say
Numeric data types
Bytes, Booleans and Integers use less memory than Longs. That's true. However, they're not faster. Windows is 32-bit and so are Longs. If you need the utmost speed, use Longs.
Static makes your app sooo static
Did you know that Static local variables are slower than the normal Dim locals? One could think that Statics are faster as they don't need to get allocated every time you call the procedure. But it's not so. Use Dim unless you have to do Static.
Incremental ReDim Preserve
You might be tempted to use the following code to allocate more space for an array.
ReDim Preserve myarray(UBound(myarray) + 1)
This code allocates one more entry for myarray when required, keeping the array size as small as possible. This may work well for small arrays. If you repeatedly execute this line and myarray becomes large, your application locks up every time you allocate more space. It's better to allocate in larger chunks.
If arrayindex > UBound(myarray) Then ReDim Preserve myarray(UBound(myarray) + 1000) End If
This way you allocate some more entries if you go out of space. +1000 is just an example. You should consider which chunk size suits your application best. Try doubling the size, for example. Or you could start with one chunk size, and adjust the size as the array grows.
You've probably heard that replacing
Did you actually measure the effect? A With block isn't always the fastest alternative. It depends on what expressions you use and how many calls you save. Adding a With block for 1 or 2 calls is probably not worth it.
The bang (!) operator can lead to late binding. Although your code looks short and optimized, it runs slowly. Try the alternatives, if you have any.
A word about those DLLs and OCXs
VB is slow. Other languages are fast. You get better performance withs DLLs, OCXs and as little VB code as possible.
Wrong! Stay away from extra run-times unless you know what you're doing. You can often write the same functionality in pure VB. This way you not only save the distribution of the run-times, but your code might actually execute faster. Don't take our word for it. Get VB Watch Profiler and time your code.
More optimization readings