Numeric variables give
Run Time 6` error
It all seems to be related to the way Excel on MacOs handles these declarations. I find with Integer, Single, and Double if you do a division you get the error.
Dim x, y as double
x=2
y=2 'error 6
x=x/2
y=y/2 'error6
End Sub
If you put x and y in Watch window you will see they are not showing as Double; instead, x is displayed as Variant/String, y as String.
The Variant/String performs ok, the string does not.
MS Docs state that Dim x,y As Double will declare both to be doubles. Others, who I assume are on Windows, say not, that you must say Dim x As Double, y As Double; but in this case, even that does not work.
MacOs Excel Version 16.43
This is the correct syntax:
Dim x As Double
Dim y As Double
x = 2
y = 2
x = x / 2
y = y / 2
' No error.
Related
Some background...
I am currently building a macro that will estimate the cost of an injection molding tool. These tools have cavities which are filled with plastic. The number of cavities a tool has is the number of parts that will be formed.
So far my program will determine the minimum number of cavities a tool can have based on customer demand. This number is always even. The tool should have an even number of cavities. Given the bounding length and width of a cavity, and setting a limit to how much space the cavities can occupy within the tool, I need my program to calculate the combination of number of cavities along the length and width whose difference is minimized and whose product is equal to the total number of minimum cavities the tool should have.
I am programming my macro is SolidWorks VBA. I first constructed this problem in Excel and used the solver tool. But, I am unable to find a way to reference the Excel Solver Tool in SolidWorks to automate this optimization problem. I am hoping to find a clever set of equations that can solve this specific problem for me. But if someone else has a better idea of what to use, that would be awesome.
Rephrasing in an optimization format...
Variables
x = number of cavities along width of tool
y = number of cavities along length of tool
z = suggested number of total cavities
Objective Function
Minimize x - y
Such that
x * y = z
x >= 1
y >= 1
x <= y
x is an integer
y is an integer
Example
My macro says that in order to meet demand, our tool needs to have at least 48 cavities. Find the number of cavities along the length and width of the tool such that the difference is minimized and the product is equal to 48. Ideally in this case the macro would return x = 6 and y = 8.
Thanks!
Just to clarify, in the question did you actually mean to Min y-x rather than Min x-y? Otherwise there is a naïve solution taking x = 1 and y = z. Min x - y = 1-z.
I don't program in VBA but here is the idea.
Since x and y are positive integers and there product is z, with x <= y. You can essentially start with x = floor(sqrt(z)) and decrement until x = 1.
For each x, check if there exists an integer y such that x * y = z. If there is, break the loop and that's the pair you are looking for. Otherwise continue until x = 1
If you need any pseudo code so you can translate it into VBA. Here it is
int x, y;
for (x = floor(sqrt(z)); x >= 1; --x)
{
y = z / x;
if (x * y == z)
break;
}
I think you can just test out a few examples. No fancy algorithm is needed.
If you relax the condition to be 2 numbers, x and y, whose product is z and with a minimum difference, then the answer is SQRT(z).
That is not an integer that meets your needs (in general). However, you can then try integers around the square root to see if they divide z. The first one you hit (i.e. minimum difference from SQRT(z)) should have the minimum difference.
If you relax the condition to be |z - x * y| is minimized, then I would recommend testing the numbers around sqrt(z). You need to check two cases -- the floor and ceiling of the square root (and the appropriate other number).
Just in case someone is needs something similar to this in the future, but can't figure out the pseudo-code I went ahead wrote it up. I wasn't sure how to output it as two values so I just threw them together as a string for the user to see.
Option Explicit
Function Factors(ByVal Test As Long) As String
Dim Val As Long
Dim i As Long
Val = Test
i = Int(Sqr(Val))
While Val / i >= 2
If Int(Val / i) * i = Val Then
Factors = i & " & " & Val / i
Exit Function
End If
i = i - 1
Wend
End Function
I am working on a MonteCarlo simulation model and part of it is to calculate the following formula:
X = Sqr(1-p)Y + Sqr(p)Z,
Where:
Y and Z are randomly obtained values based (idiosyncratic and systematic factors, respectviely) on a standard normal (inv.) distribution, calculated as:
Application.WorksheetFunction.NormInv (Rnd(), mean, sd)
p represents a correlation factor.
My aim is to square root a recalled formula, however when I try the following (inserting the first Sqr), it does not work and gives an error:
Matrix (n, sims) = (R * Sqr(Application.WorksheetFunction.NormInv(Rnd(), mean, sd))) + (Sqr(1 - R) * RandomS(s, x))
where:
R: Correlation factor
RandomS(s,x): generated matrix with Z values.
I don't want to go into too much details about the background and other variables, as the only problem I am getting is with Square Rooting the equation.
Error message I recieve reads:
Run-time error '5':
Invalid procedure call or argument
When I click debug it takes me to the formula, therefore there must be something wrong with the syntax.
Can you help with directly squaring the formula?
Thank you!
Andrew
Square root is simply Sqr.
It works fine in Excel VBA, so for example:
MsgBox Sqr(144)
...returns 12.
Just don't confuse it with the syntax for a worksheet function with is SQRT.
If you're still having an issue with your formula, tit must be with something other than the Square Root function, and I'd suggest you check the values of your variable, and make sure they are properly declared (preferably with Option Explicit at the top of the module).
Also make sure that you're passing Sqr a positive number.
Documentation: Sqr Function
I'm not a math major, but with your formula:
X = Sqr(1-p)Y + Sqr(p)Z,
...you specified how Y and Z are calculated, so calculate them separately to keep it simple:
Dim X as Double, Y as Double, Z as Double
Y = Application.WorksheetFunction.NormInv (Rnd(), mean, sd)
Z = Application.WorksheetFunction.NormInv (Rnd(), mean, sd)
Assuming the comma is not supposed to be in the formula, and having no idea what p is, your final code to calculate X is:
X = Sqr(1-p) * Y + Sqr(p) * Z
First of all I need to point out that I have never coded Visual Basic before.
I have an old spreadsheet which has some functions that are apparently written in Visual Basic. An example functions is:
Function Helmert_X(X, Y, Z, DX, Y_Rot, Z_Rot, s)
'Computed Helmert transformed X coordinate.
'Input: - _
cartesian XYZ coords (X,Y,Z), X translation (DX) all in meters ; _
Y and Z rotations in seconds of arc (Y_Rot, Z_Rot) and scale in ppm (s).
'Convert rotations to radians and ppm scale to a factor
Pi = 3.14159265358979
sfactor = s * 0.000001
RadY_Rot = (Y_Rot / 3600) * (Pi / 180)
RadZ_Rot = (Z_Rot / 3600) * (Pi / 180)
'Compute transformed X coord
Helmert_X = X + (X * sfactor) - (Y * RadZ_Rot) + (Z * RadY_Rot) + DX
End Function
I'm trying to convert these functions into C. I have almost finished but what I would like to do is to build a visual basic project that calls the functions with various parameters. Then I will have a C project which uses the same parameters and checks that the C gets the same answers as the Visual Basic.
When I put the Visual Basic functions into a Module in Visual Studio I get a lot of errors. Firstly the comments don't all register as comments, and the variables apparently need to be declared.
Am I using the functions properly? Is there anyway to use them in code without modifying them? Could I use Excel to run test parameters through the functions?
It seems you need to declare all variables that exist in that function. Try to add theses lines after the comments:
Dim Pi As Double
Dim sfactor As Double
Dim RadY_Rot As Double
Dim RadZ_Rot As Double
You can also specify type for variables that came with function, as well the function itself:
Function Helmert_X(X as Double, Y as Double, Z as Double, DX as Double, Y_Rot as Double, Z_Rot as Double, s as Double) as Double
Let me know if it works or if there is still some issue.
I am currently writing a program that contains a two dimensional newton raphson sub. it starts like this:
Sub newton11()
Dim x As Double, z As Double, tolerance As Double
Dim error_x As Double, error_z As Double
Dim iteration As Integer
iteration = 0
tolerance = 0.05
x = Range("h19").value
z = Range("h20").value
however when I run the sub, it doesn't work. When I was debugging I noticed when I hovered over x it was assigned a value of -344 when Range("h19") is 53 and z was assigned -5.12 when Range("20") is 0.
does anybody know how to fix this?
Always define the sheet where you pull the data from. If you write:
x = Range("H19").Value
by default you're saying:
x = ActiveSheet.Range("H19").Value
which is probably containing the value -344 while you were waiting for 53. With this:
x = Sheets("myGoodSheet").Range("H13").Value
you're sure you're referencing to the proper one. And as Mark says in his comment, even better if you reference the correct workbook with Workbooks(j) just in front of the Sheets collection.
What you're describing isn't possible.
Instead of this:
x = Range("h19").value
z = Range("h20").value
Extract variables:
Dim xRange As Range, yRange As Range
Set xRange = Range("h19")
Set yRange = Range("h20")
x = xRange.Value
y = yRange.Value
Now place a breakpoint on the x = xRange.Value line, and use the locals window (from the View menu) to inspect the runtime value of xRange and yRange - then F8 and inspect the runtime value of x: the two are the same.
See #Matteo's answer for the why.
Public Function foo()
Dim x As Double, y As Double, z As Double
x = 1.26
y = 3.175
z = Round(x + y, 2)
foo = z
End Function
Running Excel 2007 on Windows 7. This function returns 4.43 into a cell with =foo() which is annoying as I want 4.44. I found some documentation claiming VBA ROUND uses even rounding but here the last digit is odd. What is wrong here?
You can always use the Worksheet Round Function instead of VBA's built-in one
Public Function foo2()
Dim x As Double, y As Double, z As Double
x = 1.26
y = 3.175
z = Application.WorksheetFunction.Round(x + y, 2)
foo2 = z
End Function
foo2 will result in 4.44 (tested on my machine). I don't know if this would affect performance at all.
You will need to use decimal types to accomplish this which uses integer based arithmetic as opposed to floating point based.
Excel doesn't have a native data type for this, so you have to use a Variant and then convert to a decimal using the CDec function.
Public Function foo()
Dim x As Variant, y As Variant, z As Variant
x = CDec(1.26)
y = CDec(3.175)
z = Round(x + y, 2)
foo = z
End Function
While Excel.WorksheetFunction.Round does perform correct 4/5 rounding, it is terribly slow and, of course, requires Excel to be installed.
For fast and precise rounding of any value - up, down, 4/5, Banker's, significant digits, Base 2 or Base 10, and more - go to my project VBA.Round.