Accumulate number of VBA function is not working - vba

I am trying to use VBA function to add up a number's all power result together.
For example if I have 6 as revenue, and have first=1 and last=5, diff=5-1=4, then the result should be like total=6+6^2+6^3+6^4.
Below is my VBA code and not sure why it is not working and always give me result as 0:
Function AC(last, first, revenue)
diff = last - firs
For i = 1 To diff
Count = revenue ^ i
Total = Total + Count
Next i
End Function
Thanks if anyone can help me

You need to assign a value to the Function for it to return a value. You also have a spelling error on diff = last - firs :
Function AC(last, first, revenue)
diff = last - first
For i = 1 To diff
Count = revenue ^ i
Total = Total + Count
Next i
AC = Total
End Function
To be safe one should also always declare the variables, and we can do the addition right to the function:
Option Explicit
Function AC(ByVal last As Long, ByVal first As Long, ByVal revenue As Double) As Double
Dim diff As Long
Dim i as long
Dim Count as Double
diff = last - first
For i = 1 To diff
Count = revenue ^ i
AC = AC + Count
Next i
End Function

With array formula AC = [sum(6 ^ row(1:4))] ( # is short for As Double) :
Function AC#(last#, first#, revenue#)
AC = Evaluate("sum(" & revenue & " ^ row(1:" & last - first & "))")
End Function
With Excel Formula:
=SUMPRODUCT(revenue ^ ROW(INDIRECT("1:" & last - first)))

Here's a loop-less implementation:
Function AC(last, first, revenue)
If revenue = 1 then AC = last - first: Exit Function
AC = revenue*((revenue^(last - first) - 1) / (revenue-1))
End Function

Related

BigInteger Innacuracy

In the following project euler program #56, Considering natural numbers of the form, a^b, where a, b < 100, what is the maximum digital sum?
so I wrote the following code:
Dim num As System.Numerics.BigInteger
Dim s As String
Dim sum As Integer
Dim record As Integer
For a = 2 To 99
For b = 1 To 99
num = a ^ b
s = num.ToString
For i = 0 To s.Length - 1
sum += CInt(s.Substring(i, 1))
Next
sum = 0
Next
Next
The answer I got from the program was not the correct answer, so I wrote the following code so I can see what numbers set a new high value and see if something is wrong.
If sum > record Then
record = sum
Console.WriteLine(a & "," & b)
End If
One of the answers was a=10 b= 81. Obviously that doesn't make sense, because that value is 1 + 81 "0" = 1, but watching the result of 10^81, was 999999999999999921281879895665782741935503249059183851809998224123064148429897728
I searched about the accuracy of BigInteger but couldn't find anything, is there something that I'm missing?

Excel VBA continually returning 0

I'm trying to calculate a cross currency rate by simply summing the forex rates for A/B and B/C and multiplying the means to find the A/C rate and I keep getting 0 in return. This is the code:
Function forex(audData As Range, euData As Range)
a = Application.Count(audData)
e = Application.Count(euData)
'Counts how many values are in the data
aSum = 0
eSum = 0
aMean = 0
eMean = 0
For i = 1 To aud ' This sums the 1st forex rate and finds the mean
aSum = aSum + audData(i)
Next i
aMean = aSum / a
For i = 1 To eu ' This sums the 2nd forex rate and finds the mean
eSum = eSum + euData(i)
Next i
eMean = eSum / e
forex = (aMean * eMean)
End Function
You could use the Average() function:
Function forex(audData As Range, euData As Range)
With WorksheetFunction
forex = .Average(audData) * .Average(euData)
End With
End Function
You seem to be a victim of undeclared variables. You have two loops,
For i = 1 To aud
and (later on)
For i = 1 To eu
where neither aud nor eu are declared. Thus, they default to variants with an implicit value of 0, hence neither of these loops ever execute and all your variables stay at 0.
You really should get in the habit of using Option Explicit at the top of all of your modules. This can be done automatically by enabling the option Require Variable Declarations in the VBA editor options. In the long run, it will save you hours of debugging time.
I can't test your code, but if you declare your variables and replace aud and eu by what I think you meant you would get:
Function forex(audData As Range, euData As Range) As Double
Dim a As Long, e As Long, aSum As Double, eSum As Double, aMean As Double, eMean As Double, i As Long
a = Application.Count(audData)
e = Application.Count(euData)
'Counts how many values are in the data
For i = 1 To a ' This sums the 1st forex rate and finds the mean
aSum = aSum + audData(i)
Next i
aMean = aSum / a
For i = 1 To e ' This sums the 2nd forex rate and finds the mean
eSum = eSum + euData(i)
Next i
eMean = eSum / e
forex = (aMean * eMean)
End Function
I skipped the lines like aSum = 0 since properly declared VBA variables have reasonable default values.

MS Excel. VBA function returns #value

It would be nice if someone could explain what causes function above return #value error.
Public Function papild(x)
Dim Sum As Double, A As Double, pi As Double,
Sum = 0.5 - (x - pi / 4)
A = -(x - pi / 4)
pi = Application.WorksheetFunction.pi()
Dim k As Integer, i As Integer
k = 2
i = 0
Do While Abs(A) > 0.0001
A = -A * 4 * A * A / (k + i) * (k + i + 1)
Sum = Sum + A
k = k + 1
i = i + 1
Loop
paplid = Sum
End Function
Function takes x value from MS Excel cell and it's equal = -1.5708 (=-PI()/2 #Formula Bar)
In lines 3 and 4 you work with variable pi before setting it in line 5...
Could there be some brackets missing in your formula. It basically says:
A = -4A^3 * (k+i+1)/(k+1)
This obviously drifts to +/- infinite so your loop cannot end.
Also there is a comma too much in the second line and a spelling error in the last line (paplid instead of papild).
Have you tried debugging the code?
When I run the code I get an overflow error # the 6th iteration of the while loop starting with x = -1.5708. Number gets to large to fit inside variable
.Other than that there are some minor things:
missing As Double
Public Function papild(x) As Double
and unnecessary comma at the end
Dim Sum As Double, A As Double, pi As Double,

Rounding up to nearest higher integer in VBA

I'm trying to calculate how many layers a commodity will be stacked in. I have a variable quantity (iQty), a given width for the loadbed (dRTW), a width per unit for the commodity (dWidth) and a quantity per layer (iLayerQty).
The quantity per layer is calculated as iLayerQty = Int(dRTW/dWidth)
Now I need to divide the total quantity by the quantity per layer and round up. In an Excel formula it would be easy, but I'm trying to avoid WorksheetFunction calls to minimise A1/R1C1 confusion. At the moment I'm approximating it with this:
(Number of layers) = ((Int(iQty / iLayerQty) + 1)
And that works fine most of the time - except when the numbers give an integer (a cargo width of 0.5 m, for instance, fitting onto a 2.5 m rolltrailer). In those instances, of course, adding the one ruins the result.
Is there any handy way of tweaking that formula to get a better upward rounding?
I don't see any reason to avoid WorksheetFunction; I don't see any confusion here.
Number_of_layers = WorksheetFunction.RoundUp(iQty / iLayerQty, 0)
You could also roll your own function:
Function RoundUp(ByVal Value As Double)
If Int(Value) = Value Then
RoundUp = Value
Else
RoundUp = Int(Value) + 1
End If
End Function
Call it like this:
Number_of_layers = RoundUp(iQty / iLayerQty)
If using a WorksheetFunction object to access a ROUNDUP or CEILING function is off the table then the same can be accomplished with some maths.
Number of layers = Int(iQty / iLayerQty) - CBool(Int(iQty / iLayerQty) <> Round(iQty / iLayerQty, 14))
A VBA True is the equivalent of (-1) when used mathematically. The VBA Round is there to avoid 15 digit floating point errors.
I use -int(-x) to get the ceiling.
?-int(-1.1) ' get ceil(1.1)
2
?-int(1.1) ' get ceil(-1.1)
-1
?-int(-5) ' get ceil(5)
5
These are the functions I put together for this purpose.
Function RoundUp(ByVal value As Double) as Integer
Dim intVal As Integer
Dim delta As Double
intVal = CInt(value)
delta = intVal - value
If delta < 0 Then
RoundUp = intVal + 1
Else
RoundUp = intVal
End If
End Function
Function RoundDown(ByVal value As Double) as Integer
Dim intVal As Integer
Dim delta As Double
intVal = CInt(value)
delta = intVal - value
If delta <= 0 Then
RoundDown = intVal
ElseIf delta > 0 Then
RoundDown = intVal - 1
End If
End Function
This is my Ceiling in VBA.
Function Ceiling(ByVal Number As Double, ByVal Significance As Double) As Double
Dim intVal As Long
Dim delta As Double
Dim RoundValue As Double
Dim PreReturn As Double
If Significance = 0 Then
RoundValue = 1
Else
RoundValue = 1 / Significance
End If
Number = Number * RoundValue
intVal = CLng(Number)
delta = intVal - Number
If delta < 0 Then
PreReturn = intVal + 1
Else
PreReturn = intVal
End If
Ceiling = PreReturn / RoundValue
End Function

Want to plot a graph by avg the values

I want to plot a graph in Vb.net. I have x and y values , x indicates cycles. After every 4 cycles i want to average out all 4 cycles' value and draw a line then in the 5th cycle's graph shows its real graph value and then when cycles reach the 8th cycle then once again average out the value from the starting and plot a straight line. How can I plot this graph?
Private _averageValue As Double
Public ReadOnly Property AverageValue() As Double
Get
Return _averageValue
End Get
End Property
Private Sub CalculateAverageValue()
Try
Dim sum As Double = 0
Dim cnt As Integer = 1
_Reading = ""
'loop to find the average
If _SeparatedValues.Count > 0 Then
For cnt = 1 To _SeparatedValues.Count
sum = sum + _SeparatedValues(cnt - 1)
_Reading = _Reading & " " & _SeparatedValues(cnt - 1)
Next
_Reading = _Reading.Trim
_averageValue = sum / (cnt - 1)
Else
_averageValue = 0
End If
Catch ex As Exception
End Try
End Sub