Consider a convergent serie in the form:
sum(((-1)^n)*something)
where n is the index of iteration (n goes from 1 to infinity).
If we implement direclty the formula, we have std::pow(-1, n) but is there a more "rapid" algorithmic trick to implement that ?
Check whether n is even or odd,
(n % 2 == 0) ? 1 : -1;
does it. If you want to avoid a branch,
1 - 2*(n & 1)
I'm assuming that sum(((-1)^n)*something) is pseudocode, and n is a variable bound by sum.
Let's extend that notation to sum(n <- [0,1,2,3..], ((-1)^n)*f(n)). Your best option would probably be to first split this into two sums, that you add together:
sum(n <- [0,2..], ((-1)^n)*f(n)) + sum(n <- [1,3..], ((-1)^n)*f(n))
In the first term, n is always even, so (-1)^n will always be +1. Analogously, in the second term, it will always be -1. We can now rewrite this as follows:
sum(n <- [0,2..], f(n)) + sum(n <- [1,3..], -f(n))
Since every term in the second sum is multiplied by a constant, we can move that constant out of the sum:
sum(n <- [0,2..], f(n)) - sum(n <- [1,3..], f(n))
Now, let's make sure these sums take the same sequences of indices, and substitute 2*m and 2*m+1 for n:
sum(m <- [0,1..], f(2*m)) - sum(m <- [0,1..], f(2*m+1))
Now we can unite these sums again:
sum(m <- [0,1..], f(2*m) - f(2*m+1))
Or, if you want pseudo-C:
T result = 0;
for(m = 0; m < limit; m+=2) {
result += f(m);
result -= f(m+1);
}
This saves you a multiplication by +1 or -1, as most seem to suggest here. Since your sequence is convergent, taking an extra term should not negatively influence the correctness of the answer.
Yeah, there is a magic trick: (-1)^n == 1 if and only if n is even, and (-1)^n == -1 if and only if n is odd. Thus:
int p = (n % 2 == 0) ? 1 : -1;
sum(p*something)
If you are doing this in a loop, you could simply do:
x = 1; // Assuming we start on n = 0
for(...) // or while(...)
{
sum += x * something;
x = -x;
}
This is most likely a lot faster than doing checks on n - of course, it DOES assume that all n values are iterated over, and you are not skipping a few here and there...
The term ((-1)^n)*something evaluates to -something for odd n, or something for even n:
n & 1 ? -something : something
If something is a constant value, then sum(((-1)^n)*something) evaluates to -something when the last value of n is odd, or 0 for an even number of summands:
n & 1 ? -something : 0
In this case, the serie would not be convergent.
Related
I have two algorithms that solve this problem: Generate all sequences of bits within Hamming distance t. Now I want to compare them theoretically (I do have time measurements, if needed).
The iterative algorithm has a complexity of:
O((n choose t) * n)
where n is the length of the bit-string and t is the desired Hamming distance.
The recursive algorithm, they best we have so far is:
O(2^n)
but how to compare these two Time Complexities, without introducing t inside the second Time Complexity? For that reason, I am trying to do that, can you help?
The recursive algorithm:
// str is the bitstring, i the current length, and changesLeft the
// desired Hamming distance (see linked question for more)
void magic(char* str, int i, int changesLeft) {
if (changesLeft == 0) {
// assume that this is constant
printf("%s\n", str);
return;
}
if (i < 0) return;
// flip current bit
str[i] = str[i] == '0' ? '1' : '0';
magic(str, i-1, changesLeft-1);
// or don't flip it (flip it again to undo)
str[i] = str[i] == '0' ? '1' : '0';
magic(str, i-1, changesLeft);
}
The recursive algorithm is O((n choose t) * n) too, by an analysis that charges to each printed combination the cost of the entire call stack at the time that it is printed. We can do this because every invocation of magic (except the two O(1) leaf calls where i < 0, which we could easily do away with) prints something.
This bound is best possible if you assign printing its true cost. Otherwise, I'm pretty sure that both analyses can be tightened to O(n choose t) excluding printing for t > 0, with details in Knuth 4A.
At the most general level of time complexity, we have a "worst case" of t = n/2. Now, fix t and gradually increment n. Let's take a starting point of n=8, t=4
C(8 4) = 8*7*6*5*4*3*2*1 / (4*3*2*1 * 4*3*2*1)
= 8*7*6*5 / 24
n <= n+1 ... n choose t is now
C(9 4) = ...
= 9*8*7*6 / 24
= 9/5 of the previous value.
Now, the progression is a little easier to watch.
C( 8 4) = 8*7*6*5 / 24
C( 9 4) = 9/5 * C( 8 4)
C(10 4) = 10/6 * C( 9 4)
C(11 4) = 11/7 * C(10 4)
...
C( n 4) = n/(n-4) * C(n-1 4)
Now, as lemmas for the student:
Find the base complexity, n! / ( (n-1)! ^ 2)
Find the combinatorial complexity of product (n / (n-c)) for constant c
Input.
I have a bit array sized n and two integers, 1<=i<=n and 0<=j<=n.
i indicates the maximum of subsequent numbers that can be 0. j indicates the maximum of subsequent numbers that can be 1.
Desired Output
I search for a method that returns all possible bit arrays sized n that fulfill these constraints.
Just looping through all array combinations (first without constraints) would result in exponential time. (Especially if i/j>>1. I suppose you can do better).
How can I effectively find those bitmask combinations?
Example
Input: i = 1, j = 2, n = 3
Result: Possible arrays are [0,1,0], [1,0,1],[1,1,0],[0,1,1].
This is nice problem for dynamic programming solution. It is enough to have method that returns number of strings starting with given digit (0 or 1) with given length. Than number of digits of length n is sum of strings starting with 0 and starting with 1.
Simple python solution with memoization is:
_c = {} # Cache
def C(d, n, ij):
if n <= 1:
return 1
if (d, n) not in _c:
_c[(d, n)] = sum(C(1-d, n-x, ij) for x in xrange(1, min(ij[d], n)+1))
return _c[(d, n)]
def B(n, i, j):
ij = [i, j] # Easier to index
_c.clear() # Clears cache
return C(0, n, ij) + C(1, n, ij)
print B(3, 1, 2)
print B(300, 10, 20)
Result is:
4
1896835555769011113367758506440713303464223490691007178590554687025004528364990337945924158
Since value for given digit and length depends on values of opposite digit and length less than given length, solution can be also obtained by calculating values increasingly by length. Python solution:
def D(n, i, j):
c0 = [1] # Initialize arrays
c1 = [1]
for x in xrange(1, n+1): # For each next digit calculate value
c0.append(sum(c1[x-y] for y in xrange(1, min(i, x)+1)))
c1.append(sum(c0[x-y] for y in xrange(1, min(j, x)+1)))
return c0[-1] + c1[-1] # Sum strings starting of length n with 0 and 1
print D(3, 1, 2)
print D(300, 10, 20)
Later approach is easier to implement in C++.
Given an input n , find the sum of all the possible combinations of numbers 1 ... n.
For example, if n=3 , then all the possible combinations are
(1),(2),(3),(1,2),(1,3),(2,3),(1,2,3)
and their sum is
1 + 2 + 3 + (1+2) + (1+3) + (2+3) + (1+2+3) =24
I am able to solve this problem using recursion. How can I solve this problem using Dynamic Programming ?
#include<iostream>
using namespace std;
int sum=0,n;
int f(int pos,int s)
{
if(pos>n)
{
return 0;
}
else
{
for(int i=pos+1;i<=n;++i)
{
sum+=s+i;
f(i,s+i);
}
}
}
int main()
{
cin>>n;
sum=0;
f(0,0);
cout<<sum<<'\n';
}
}
EDIT
Though this problem can be solved in constant time using this series.
But I want to know how this can be done using Dynamic Programming as I am very weak at it.
You do not need to use dynamic programming; you can use simple arithmetic if you want.
The number of cases is 2 ^ n, since each number is either on or off for a given sum.
Each number from 1 to n is used in exactly half of the sums, so each number comes 2 ^ (n-1) times.
1 + 2 + ... + n = (n - 1) * n / 2.
So the sum is (n - 1) * n / 2 * 2 ^ (n-1).
For n = 3, it is (4*3/2) * 4 = 24.
EDIT: if you really want to use dynamic programming, here's one way.
Dynamic programming makes use of saving the results of sub-problems to make the super problem faster to solve. In this question, the sub-problem would be the sum of all combinations from 1 ... n-1.
So create a mapping from n -> (number of combinations, sum of combinations).
Initialize with 1 -> (2,1). Because there are two combinations {0,1} and the sum is 1. Including 0 just makes the math a bit easier.
Then your iteration step is to use the mapping.
Let's say (n-1) -> (k,s), meaning there are k sets that sum to s for 1 ... n-1.
Then the number of sets for n is k * 2 (each combination either has n or does not).
And the sum of all combinations is s + (s + k * n), since you have the previous sum (where n is missing) plus the sum of all the combinations with n (which should be k * n more than s because there are k new combinations with n in each).
So add n -> (2*k,2*s + k*n).
And your final answer is the s in n -> (k,s).
let dp[n] be the result, Therefore:
dp[1] = 1
dp[n] = 2 * dp[n-1] + 2^(n-1) * n
First, it is obvious that dp[1] = 1
Second, dp[n] is the sum which contains n and sum which didn't contains n
E.G: dp[3] = {(1) (2) (1,2)} + {(3), (1,3), (2,3), (1,2,3)}
We can find dp[n-1] appear twice and the number of n appear 2^(n-1) times
I think maybe it is what you want.
For any whole number input W restricted by the range R = [x,y], the "overflow," for lack of a better term, of W over R is W % (y-x+1) + x. This causes it wrap back around if W exceeds y.
As an example of this principle, suppose we iterate over a calendar's months:
int this_month = 5;
int next_month = (this_month + 1) % 12;
where both integers will be between 0 and 11, inclusive. Thus, the expression above "clamps" the integer to the range R = [0,11]. This approach of using an expression is simple, elegant, and advantageous as it omits branching.
Now, what if we want to do the same thing, but backwards? The following expression works:
int last_month = ((this_month - 1) % 12 + 12) % 12;
but it's abstruse. How can it be beautified?
tl;dr - Can the expression ((x-1) % k + k) % k be simplified further?
Note: C++ tag specified because other languages handle negative operands for the modulo operator differently.
Your expression should be ((x-1) + k) % k. This will properly wrap x=0 around to 11. In general, if you want to step back more than 1, you need to make sure that you add enough so that the first operand of the modulo operation is >= 0.
Here is an implementation in C++:
int wrapAround(int v, int delta, int minval, int maxval)
{
const int mod = maxval + 1 - minval;
if (delta >= 0) {return (v + delta - minval) % mod + minval;}
else {return ((v + delta) - delta * mod - minval) % mod + minval;}
}
This also allows to use months labeled from 0 to 11 or from 1 to 12, setting min_val and max_val accordingly.
Since this answer is so highly appreciated, here is an improved version without branching, which also handles the case where the initial value v is smaller than minval. I keep the other example because it is easier to understand:
int wrapAround(int v, int delta, int minval, int maxval)
{
const int mod = maxval + 1 - minval;
v += delta - minval;
v += (1 - v / mod) * mod;
return v % mod + minval;
}
The only issue remaining is if minval is larger than maxval. Feel free to add an assertion if you need it.
k % k will always be 0. I'm not 100% sure what you're trying to do but it seems you want the last month to be clamped between 0 and 11 inclusive.
(this_month + 11) % 12
Should suffice.
The general solution is to write a function that computes the value that you want:
//Returns floor(a/n) (with the division done exactly).
//Let ÷ be mathematical division, and / be C++ division.
//We know
// a÷b = a/b + f (f is the remainder, not all
// divisions have exact Integral results)
//and
// (a/b)*b + a%b == a (from the standard).
//Together, these imply (through algebraic manipulation):
// sign(f) == sign(a%b)*sign(b)
//We want the remainder (f) to always be >=0 (by definition of flooredDivision),
//so when sign(f) < 0, we subtract 1 from a/n to make f > 0.
template<typename Integral>
Integral flooredDivision(Integral a, Integral n) {
Integral q(a/n);
if ((a%n < 0 && n > 0) || (a%n > 0 && n < 0)) --q;
return q;
}
//flooredModulo: Modulo function for use in the construction
//looping topologies. The result will always be between 0 and the
//denominator, and will loop in a natural fashion (rather than swapping
//the looping direction over the zero point (as in C++11),
//or being unspecified (as in earlier C++)).
//Returns x such that:
//
//Real a = Real(numerator)
//Real n = Real(denominator)
//Real r = a - n*floor(n/d)
//x = Integral(r)
template<typename Integral>
Integral flooredModulo(Integral a, Integral n) {
return a - n * flooredDivision(a, n);
}
Easy Peasy, do not use the first module operator, it is superfluous:
int last_month = (this_month - 1 + 12) % 12;
which is the general case
In this instance you can write 11, but I would still do the -1 + 11 as it more clearly states what you want to achieve.
Note that normal mod causes the pattern 0...11 to repeat at 12...23, 24...35, etc. but doesn't wrap on -11...-1. In other words, it has two sets of behaviors. One from -infinity...-1, and a different set of behavior from 0...infinity.
The expression ((x-1) % k + k) % k fixes -11...-1 but has the same problem as normal mod with -23...-12. I.e. while it fixes 12 additional numbers, it doesn't wrap around infinitely. It still has one set of behavior from -infinity...-12, and a different behavior from -11...+infinity.
This means that if you're using the function for offsets, it could lead to buggy code.
If you want a truly wrap around mod, it should handle the entire range, -infinity...infinity in exactly the same way.
There is probably a better way to implement this, but here is an easy to understand implementation:
// n must be greater than 0
func wrapAroundMod(a: Int, n: Int) -> Int {
var offsetTimes: Int = 0
if a < 0 {
offsetTimes = (-a / n) + 1
}
return (a + n * offsetTimes) % n
}
Not sure if you were having the same problem as me, but my problem was essentially that I wanted to constrain all numbers to a certain range. Say that range was 0-6, so using %7 means that any number higher than 6 will wrap back around to 0 or above. The actual problem is that numbers less than zero didn't wrap back around to 6. I have a solution to that (where X is the upper limit of your number range and 0 is the minimum):
if(inputNumber <0)//If this is a negative number
{
(X-(inputNumber*-1))%X;
}
else
{
inputNumber%X;
}
I just saw this question and have no idea how to solve it. can you please provide me with algorithms , C++ codes or ideas?
This is a very simple problem. Given the value of N and K, you need to tell us the value of the binomial coefficient C(N,K). You may rest assured that K <= N and the maximum value of N is 1,000,000,000,000,000. Since the value may be very large, you need to compute the result modulo 1009.
Input
The first line of the input contains the number of test cases T, at most 1000. Each of the next T lines consists of two space separated integers N and K, where 0 <= K <= N and 1 <= N <= 1,000,000,000,000,000.
Output
For each test case, print on a new line, the value of the binomial coefficient C(N,K) modulo 1009.
Example
Input:
3
3 1
5 2
10 3
Output:
3
10
120
Notice that 1009 is a prime.
Now you can use Lucas' Theorem.
Which states:
Let p be a prime.
If n = a1a2...ar when written in base p and
if k = b1b2...br when written in base p
(pad with zeroes if required)
Then
(n choose k) modulo p = (a1 choose b1) * (a2 choose b2) * ... * (ar choose br) modulo p.
i.e. remainder of n choose k when divided by p is same as the remainder of
the product (a1 choose b1) * .... * (ar choose br) when divided by p.
Note: if bi > ai then ai choose bi is 0.
Thus your problem is reduced to finding the product modulo 1009 of at most log N/log 1009 numbers (number of digits of N in base 1009) of the form a choose b where a <= 1009 and b <= 1009.
This should make it easier even when N is close to 10^15.
Note:
For N=10^15, N choose N/2 is more than
2^(100000000000000) which is way
beyond an unsigned long long.
Also, the algorithm suggested by
Lucas' theorem is O(log N) which is
exponentially faster than trying to
compute the binomial coefficient
directly (even if you did a mod 1009
to take care of the overflow issue).
Here is some code for Binomial I had written long back, all you need to do is to modify it to do the operations modulo 1009 (there might be bugs and not necessarily recommended coding style):
class Binomial
{
public:
Binomial(int Max)
{
max = Max+1;
table = new unsigned int * [max]();
for (int i=0; i < max; i++)
{
table[i] = new unsigned int[max]();
for (int j = 0; j < max; j++)
{
table[i][j] = 0;
}
}
}
~Binomial()
{
for (int i =0; i < max; i++)
{
delete table[i];
}
delete table;
}
unsigned int Choose(unsigned int n, unsigned int k);
private:
bool Contains(unsigned int n, unsigned int k);
int max;
unsigned int **table;
};
unsigned int Binomial::Choose(unsigned int n, unsigned int k)
{
if (n < k) return 0;
if (k == 0 || n==1 ) return 1;
if (n==2 && k==1) return 2;
if (n==2 && k==2) return 1;
if (n==k) return 1;
if (Contains(n,k))
{
return table[n][k];
}
table[n][k] = Choose(n-1,k) + Choose(n-1,k-1);
return table[n][k];
}
bool Binomial::Contains(unsigned int n, unsigned int k)
{
if (table[n][k] == 0)
{
return false;
}
return true;
}
Binomial coefficient is one factorial divided by two others, although the k! term on the bottom cancels in an obvious way.
Observe that if 1009, (including multiples of it), appears more times in the numerator than the denominator, then the answer mod 1009 is 0. It can't appear more times in the denominator than the numerator (since binomial coefficients are integers), hence the only cases where you have to do anything are when it appears the same number of times in both. Don't forget to count multiples of (1009)^2 as two, and so on.
After that, I think you're just mopping up small cases (meaning small numbers of values to multiply/divide), although I'm not sure without a few tests. On the plus side 1009 is prime, so arithmetic modulo 1009 takes place in a field, which means that after casting out multiples of 1009 from both top and bottom, you can do the rest of the multiplication and division mod 1009 in any order.
Where there are non-small cases left, they will still involve multiplying together long runs of consecutive integers. This can be simplified by knowing 1008! (mod 1009). It's -1 (1008 if you prefer), since 1 ... 1008 are the p-1 non-zero elements of the prime field over p. Therefore they consist of 1, -1, and then (p-3)/2 pairs of multiplicative inverses.
So for example consider the case of C((1009^3), 200).
Imagine that the number of 1009s are equal (don't know if they are, because I haven't coded a formula to find out), so that this is a case requiring work.
On the top we have 201 ... 1008, which we'll have to calculate or look up in a precomputed table, then 1009, then 1010 ... 2017, 2018, 2019 ... 3026, 3027, etc. The ... ranges are all -1, so we just need to know how many such ranges there are.
That leaves 1009, 2018, 3027, which once we've cancelled them with 1009's from the bottom will just be 1, 2, 3, ... 1008, 1010, ..., plus some multiples of 1009^2, which again we'll cancel and leave ourselves with consecutive integers to multiply.
We can do something very similar with the bottom to compute the product mod 1009 of "1 ... 1009^3 - 200 with all the powers of 1009 divided out". That leaves us with a division in a prime field. IIRC that's tricky in principle, but 1009 is a small enough number that we can manage 1000 of them (the upper limit on the number of test cases).
Of course with k=200, there's an enormous overlap which could be cancelled more directly. That's what I meant by small cases and non-small cases: I've treated it like a non-small case, when in fact we could get away with just "brute-forcing" this one, by calculating ((1009^3-199) * ... * 1009^3) / 200!
I don't think you want to calculate C(n,k) and then reduce mod 1009. The biggest one, C(1e15,5e14) will require something like 1e16 bits ~ 1000 terabytes
Moreover executing the loop in snakiles answer 1e15 times seems like it might take a while.
What you might use is, if
n = n0 + n1*p + n2*p^2 ... + nd*p^d
m = m0 + m1*p + m2*p^2 ... + md*p^d
(where 0<=mi,ni < p)
then
C(n,m) = C(n0,m0) * C(n1,m1) *... * C(nd, nd) mod p
see, eg http://www.cecm.sfu.ca/organics/papers/granville/paper/binomial/html/binomial.html
One way would be to use pascal's triangle to build a table of all C(m,n) for 0<=m<=n<=1009.
psudo code for calculating nCk:
result = 1
for i=1 to min{K,N-K}:
result *= N-i+1
result /= i
return result
Time Complexity: O(min{K,N-K})
The loop goes from i=1 to min{K,N-K} instead of from i=1 to K, and that's ok because
C(k,n) = C(k, n-k)
And you can calculate the thing even more efficiently if you use the GammaLn function.
nCk = exp(GammaLn(n+1)-GammaLn(k+1)-GammaLn(n-k+1))
The GammaLn function is the natural logarithm of the Gamma function. I know there's an efficient algorithm to calculate the GammaLn function but that algorithm isn't trivial at all.
The following code shows how to obtain all the binomial coefficients for a given size 'n'. You could easily modify it to stop at a given k in order to determine nCk. It is computationally very efficient, it's simple to code, and works for very large n and k.
binomial_coefficient = 1
output(binomial_coefficient)
col = 0
n = 5
do while col < n
binomial_coefficient = binomial_coefficient * (n + 1 - (col + 1)) / (col + 1)
output(binomial_coefficient)
col = col + 1
loop
The output of binomial coefficients is therefore:
1
1 * (5 + 1 - (0 + 1)) / (0 + 1) = 5
5 * (5 + 1 - (1 + 1)) / (1 + 1) = 15
15 * (5 + 1 - (2 + 1)) / (2 + 1) = 15
15 * (5 + 1 - (3 + 1)) / (3 + 1) = 5
5 * (5 + 1 - (4 + 1)) / (4 + 1) = 1
I had found the formula once upon a time on Wikipedia but for some reason it's no longer there :(