Generating certain sequence of numbers with defined ranges - vb.net

How can I use a collection of nested for loops (or any other type) to produce a sequence like this with these variables:
length is how many digts to go to
max is the maximum number
min is the minimum number
Lets say for this case:
length = 2
max = 3
min = 1
it would produce:
11
12
13
21
22
23
31
32
33
This works "ok" for only length = 1, but not really, since I still have annoying 0's at the start
For i = 1 To length
For ii = 0 To i
For iii = 1 To 5
Console.WriteLine(Str(ii) + Str(iii))
Next
Next
Next

As this looks like a homework problem, I am going to attempt to help you think through this problem without actually giving you the answer in code.
Let's think through this problem...
You have the range 1-3. So your first sequence is easy:
1, 2, 3
Now you want to produce a sequence from 11 to 13. What's the change, or difference, between 1 through 3 and 11 through 13? The answer is you've added 10.
The same is true for 21 through 23 - you've added 10 again.
So, what you want to do is iterate from 1 through 3.
Then, iterate from 1 through 3 this time adding 10.
Then, iterate from 1 through 3 this time adding 20.
Thinking about this, you are essentially doing this:
1
2
3
10 + 1
10 + 2
10 + 3
10 + 10 + 1
10 + 10 + 2
10 + 10 + 3
etc
Or, you could also think about it like this:
(0 * 10) + 1
(0 * 10) + 2
(0 * 10) + 3
(1 * 10) + 1
(1 * 10) + 2
(1 * 10) + 3
(2 * 10) + 1
(2 * 10) + 2
(2 * 10) + 3
etc
Can you see a pattern forming?

Related

how to split a string to multiply each single number by a value in ms access 2007

I need to split a string of 20 digits individually and multiply each single one by a value.
String (this string is in a text box) example: 11604999123400002586
After the split, I must do the following operation:
51 x 1º digit +
73 x 2º digit +
17 x 3º digit +
89 x 4º digit +
38 x 5º digit +
62 x 6º digit +
45 x 7º digit +
53 x 8º digit +
15 x 9º digit +
50 x 10º digit +
5 x 11º digit +
49 x 12º digit +
34 x 13º digit +
81 x 14º digit +
76 x 15º digit +
27 x 16º digit +
90 x 17º digit +
9 x 18º digit +
30 x 19º digit +
3 x 20º digit
In this example:
Result = 51x1 + 73x1 + 17x6 + 89x0 + 38x4 + 62x9 +
45x9 + 53x9 + 15x1 + 50x2 + 5x3 + 49x4 + 34x0 + 81x0 + 76x0 + 27x0 + 90x2
+ 9x5 + 30x8 + 3x6 = 2627
What would be the best way to do it?
In VBA you can do something like this:
Dim a(20) as Integer
a(1) = 51
a(2) = 73
…
a(20) = 3
Dim Result AS Long: Result = 0
For i = 1 to 20
Result = Result + CInt(Mid(MyString,i,1)) * a(i)
Next i
You can do it with SQL.
Create a table, say with name weights, with 2 columns:
id: Number
weight: Number
and insert these rows:
id weight
1 51
2 73
3 17
4 89
5 38
6 62
7 45
8 53
9 15
10 50
11 5
12 49
13 34
14 81
15 76
16 27
17 90
18 9
19 30
20 3
Then execute this query:
SELECT SUM(w.weight * val(mid('11604999123400002586', w.id, 1))) AS result
FROM weights AS w
Result:
2627
Consistency of structure is critical in string manipulation. Assume there will always be 20 digits in string and every record will have value.
Calculate 20 columns and add them together for the Total - here are 2:
SELECT Quotes.*, Mid([Data],1,1)*53 AS A, Mid([Data],2,1)*71 AS B, [A]+[B] AS Total FROM Quotes;
Could pull weight factor from table. DLookup is one way but domain aggregate can cause slow performance in large dataset so if weight factors will never change, probably don't want this:
SELECT Quotes.Data, Mid([Data],1,1)* DLookup("Weight","Factors","ID=1") AS A, Mid([Data],2,1)* DLookup("Weight","Factors","ID=2") AS B, [A]+[B] AS Total FROM Quotes;
A Cartesian relationship with aggregate calcs query using data and weight factors tables can calculate Total - Cartesian can also perform slowly with large dataset:
SELECT Quotes.ID, Sum(Mid([Data],[Factors].[ID],1)*[Weight]) AS Total
FROM Factors, Quotes
GROUP BY Quotes.ID;
A custom VBA function could return just the total. Call this function from query or textbox. The weight factors can be pulled from table or hard coded in an array construct.
Function GetTotal(strD) As Long
Dim rs As DAO.Recordset, x As Integer
Set rs = CurrentDb.OpenRecordset("SELECT Weight FROM Factors ORDER BY ID")
For x = 1 To 20
GetTotal = GetTotal + Mid(strD, x, 1) * rs!Weight
rs.MoveNext
Next
End Function

infix to postfix with non-commuting operators

I have a question when it comes to - / operators in postfix vs infix.
From the assignment
The input string 5 4 + 3 10 * + is equivalent to the infix expression
(5 + 4) + (3 * 10) The answer is 39.
I follow that. Then I get confused by this statement.
We also have to worry about the non-commuting operators – and / . We
will evaluate the postfix string 4 5 – as 4 – 5 and,
likewise, will evaluate 4 5 / as 4 / 5 .
When I do that however...I get different results with infix vs postfix.
Modifying the first example to include subtraction.
infix
(5 - 4) + (3 * 10) = 31
postfix
5 4 - 3 10 * +
29....right?
SO I'm confused. The results of infix and postfix are supposed to be the same right? Is this a typo in the actual assignment or am I doing something wrong?
The postfix also evaluates to 31.
Let's go through this step by step: Our expression is
5 4 - 3 10 * +
So the stack progresses as follows:
5
5 4
1 # after evaluating -, i.e. popping 5 and 4 and pushing 5 - 4
1 3
1 3 10
1 30 # after evaluating *, i.e. popping 3 and 10 and pushing 3 * 10
31 # after evaluating +, i.e. popping 1 and 30 and pushing 1 + 30
I think you may have been confused because the example is 4-5 and your example is 5-4 for the infix notation.
To evaluate the postfix 5 4 - 3 10 * +:
5 4 - = 5 - 4 = 1
3 10 * = 3 * 10 = 30
1 30 + = 1 + 30 = 31
The second statement from your assignment just clarifies that if you have something like 4 5 -, that it will be 4 - 5 and not 5 - 4.
When you're evaluating postfix you use a stack: you push operands and when you get to an operator you pop the required operands and push the evaluated result.
In the case of commutative operators like + it doesn't matter which order the operands are in. So for example:
5 4 +
can be evaluated as
PUSH 5
PUSH 4
PUSH (POP + POP)
where the first POP will yield 4 and the second POP 5. So you have really evaluated 4+5.
But in the case of non-commutative operators, this won't work. You have to evaluate 5 / 4, not 4 / 5. So you need either to use temporary variables:
PUSH 5
PUSH 4
let d = POP; // divisor = 4
let q = POP; // quotient = 5
PUSH q/d; // push the dividend
or else introduce a SWAP operation, which swaps the top two items on the stack:
PUSH 5
PUSH 4
SWAP
PUSH (POP / POP)
or else compile the postfix so as to push in the opposite order:
PUSH 4
PUSH 5
PUSH (POP/POP)
In the statement about - and /, it's 4 5 -. That's -1, i.e. 4-5.
In the longer expression: 5 4 - 3 10 * +
It's 5 - 4, because the 5 comes first. Thus, it is (5-4) + (3*10) = 31.
If it was 4 5 - 3 10 * + then that would evaluate to 29 (i.e. (4-5) + (3*10)). This doesn't have to do with prefix or postfix notation, but the order that we evaluate the arguments in, because - and / are non commutative. The assignment specifies that they will be evaluated in the "intuitive" order, i.e. that x y - means x - y.

Formula for Buy 3 get 1 Free

I'm trying to write PL/SQL to get how much you pay if you purchase a certain amount of items. If you purchase 3 items, you get 1 free.
Therefore, for every 4th item purchased one of them is free. That means I pay for 3 items if 4 items are "purchased." If 10 items are attained then 8 should be paid for, 2 are free.
p-b v_p
*** ***
1 1 = 1
2 2 = 2
3 3 = 3
4 3(1) = 3
5 3(1) + 1 = 4
6 3(1) + 2 = 5
7 3(1) + 3 = 6
8 3(1) + 3(1) = 6
9 3(1) + 3(1) + 1 = 7
10 3(1) + 3(1) + 2 = 8
11 3(1) + 3(1) + 3 = 9
12 3(1) + 3(1) + 3(1) = 9
I've got
trunc(p-b / 3 * 2.4);
but my values are inconsistent.
Sometimes it works with
trunc(p-b / 3 * 2.25);
Am I doing the formula incorrectly? I'm supposed to be using trunc or mod.
To calculate the amount of Payed/Free stuff:
DECLARE
nAmount NUMBER := '10';
nPay NUMBER;
nFree NUMBER;
BEGIN
nPay := nAmount - TRUNC(nAmount / 4);
nFree := TRUNC(nAmount / 4);
DBMS_OUTPUT.PUT_LINE('Pay: ' || nPay);
DBMS_OUTPUT.PUT_LINE('Free: ' || nFree);
END;
/
I would use trunc and modulo
SELECT p-b, (trunc(p-b /4)) * 3 + mod(p-b, 4)
FROM your_table
demo
We can use the below formula to attain the result.
Assume n = p-b
n - ( n - mod( n, 4 ) ) / 4
Eg:
SELECT n, n - (n - mod(n,4))/4 result
FROM (SELECT LEVEL n
FROM DUAL
CONNECT BY LEVEL <= 12)
in simple way the result is:
p-b - trunc(p-b / 4);

Ways to write a number as a sum

I want to write for example number 10 all the possible ways as a sum of units 3, 4, ..., n-1 (not 2)
for example i can write 10 as
10=10(units)
10=7 + 1*3 or
10=4 + 2*3 or
10=3 + 1*3 + 1*4 or
10=2 + 2*4 or ....
I dont care about the number of combinations!
I want the combinations!!! I mean an algoithm to output like this
un 3 4 5 6 7 8 9 10
-------------------
10 0 0 0 0 0 0 0 0
07 1 0 0 0 0 0 0 0
04 2 0 0 0 0 0 0 0
03 1 1 0 0 0 0 0 0
02 0 2 0 0 0 0 0 0 etc
any response is welcomed!!!
start with zero
try to add the largest possible number
store the result, if you arrive at the target sum
else if you ended with less than the target sum, go to (2)
else (if you ended with more than the target sum)
undo the last adding step, try to add one less instead. If you don't have any more smaller numbers to try, undo one more addition in past
if you run out of all possible additions, you already found all combinations and can exit.
Example:
target = 10
0
0 + 9 -> not there yet
0 + 9 + 9 -> too much, try something less
0 + 9 + 8 -> too much, try less
...
...
...
0 + 9 + 3 -> too much, cant try any less
0 + 8 -> not there yet
0 + 8 + 8 -> too much
...
...
...
0 + 8 + 3 -> too much, cant try any less
0 + 7 -> not there yet
0 + 7 + 7 -> too much
0 + 7 + 6 -> too much
...
...
...
0 + 7 + 3 -> thats it! save!
0 + 6 -> not yet
0 + 6 + 6 -> too much...
I hope you get the idea... :)
It will be much much faster, than trying all the possible combinations and selecting only the ones that sum to 10. This approach is called backtracking (https://en.wikipedia.org/wiki/Backtracking), because you try to go in some direction (adding the largest number), but when you fail (sum is too big), you track your progress back and then try something different.
You can then speed it up by trying the possibilities in more clever way (0 + 7 + 7 is too much by 4, so don't even try 0 + 7 + 6, but skip straight to 0 + 7 + 3).

Input user defined values inside multiple cells using vba

I have to manipulate range of cells in excel using VB. Can I do it in the following manner ?
Range("a1:b5")=[1 2 3 4 5 6 7 8 9 0]
I don't think so, I've never seen that syntax. One thing you can do is something like:
For Row = 1 To 5
Range("a" + CStr(Row)).Value = Row
Range("b" + CStr(Row)).Value = (Row + 5) Mod 10
Next Row
assuming that you want it set up thus:
A B
+------
1 | 1 6
2 | 2 7
3 | 3 8
4 | 4 9
5 | 5 0
You may need to use Mid(CStr(Row),2) - I can't remember off the top of my head if Cstr gives you a leading space for non-negative numbers.