For below code, when input is:
first input = 0 1 2 3 4 5 6 7 8 9
second input = 1 2 3 4 5 6 7 8 9 10
it will produce output of:
first output = 0
second output = 1
instead of taking each input quartile it take its first element, and the problem is (after testing and such), it follow with the problem in code
for (vector<int>::size_type counter = 0; (quartiles < quadro) && (counter < numstore.size()); ++counter)
{
if (counter == (quartiles/quadro * numstore.size()))
{
quaele.push_back(numstore[counter]);
if ((quartiles == 2) && (numstore.size() / 2 == 0))
quaele[quartiles-1] = (numstore[counter]+numstore[counter-1]) / 2;
++quartiles;
}
// test
cout << quartiles;
}
where the conditional in "if function" doesn't work, I mean on first loop, counter == 0, how can 0 == 1(quartiles)/4(quadro) * 10(numstore.size()??
Because quartiles and quadro are both integers and the first is always less than the second (because that's what the for statement says), the expression:
quartiles / quadro * numstore.size()
will always be equal to zero, because quartiles / quadro is calculated first. Hence, the if statement will only ever be true the first time through the loop.
You may be able to get around this by re-arranging the calculation:
quartiles * numstore.size() / quadro
That's how integer arithmetic works. 1/4 is truncated to zero.
You can get the correct result (rounded down to the nearest integer) by multiplying first:
(quartiles * numstore.size()) / quadro
I've used parentheses to make the evaluation order clear - you could leave them out if you prefer.
Note that, for large values, you'll need to be careful that the multiplication doesn't overflow - perhaps by converting to a wider type, or to floating point, or by carefully multiplying and dividing by smaller factors. That is probably not an issue in this case.
The expression quartiles/quadro * numstore.size() will be 0 for the case where quartiles = 1 and quadro = 4. This is because 1/4 is rounded downwards to 0.
Maybe this is what you mean: (quartiles * numstore.size()) / quadro
In C++, the division operator can be thought of as two different operators: one that works on integer operands, and one that works on floating point operands. If the operands are of a floating point type, the division operator will return a floating point value.
http://www.learncpp.com/cpp-programming/eight-c-programming-mistakes-the-compiler-wont-catch/
Try:
float result = quartiles/quadro * numstore.size();
edit: correcting thanks to the comments.
float result = quartiles/(float)quadro * numstore.size();
It is enough to convert one of the operands to a floating point number.
quartiles/quadro is equal to 0.25 and because quartiles is type int quartiles/quadro == 0
In C++ when you divide two integer, you get integer division. Moreover, * and / have the same precedence, so the parser interprets it as (quartiles / quadro) * numstore.size(). And (1 / 4) is equal to 0.
Related
I was basically trying to find the number obtained on multiplying 2 with the quotient obtained on dividing 5e+8 with 3. I tried a couple of ways as shown in the snippet with GNU C++17 and got the correct answer only in the Approaches 2 and 4. I was first expecting it to be some sort of overflow situation however the maximum number that a signed int can store is a little more than 2e+9 which is much greater than the numbers which I was dealing with so I think that the issue might be something else. It would be great if someone could help out. Thanks in advance : )
using namespace std;
int main(){
// I basically wan't to calculate: 2 * 500000000/3 ( 2 * 5e+8 / 3)
// Approach 1
cout<<2 * 500000000 / 3<<"\n"; // output : 333333333 (nine 3s) WRONG!
// Approach 2
int a = 500000000/3; // output : 333333332 (eight 3s) CORRECT!
cout<<2 * a<<"\n";
// Approach 3
a = 2 * 500000000/3; // output : 333333333 (nine 3s) WRONG!
cout<<a<<"\n";
// Approach 4
cout<<500000000 / 3 * 2<<"\n"; // output : 333333332 (eight 3s) CORRECT!
}
We can verify that both the answers are in fact correct my hand.
(2*500,000,000)/3 = (1000,000,000)/3=333,333,333
and
(500,000,000/3)*2 = (166,666,666)*2 =333,333,332
This has to do with how in C++ integer division always rounds down and nothing to do with overflow. Arguably 333,333,333 is more accurate approximation of the "real" answer 333,333,333.333...
Order of operations matters. When you calculate 2 * 500000000 / 3, it's equal to
floor(floor(2 * 500000000)/3)
(in the mathematical meaning of operations on real numbers), while the calculation of 2 * (500000000/3), which is your second approach, is equal to
floor(2 * floor(500000000/3)).
This is because each integer arithmetic operation is always followed by rounding towards zero (which for non-negative result is the same as floor).
Approach 3 is equivalent to 1, and approach 4 is equivalent to 2.
Let's say I am given integers x and y (satisfying x <= y with ones digit of 0 so they are, in particular, divisible by two). Then I know that their average avg = ((x+y) / 2) is an integer as well. I would like to find this midpoint rounded up to a resolution of 100. In other words if my two inputs are 75200 and 75300 then the avg is 75250 and rounded up to the nearest 100 (but without exceeding or equaling the bigger number) forces the answer to be 75200.
How can I implement this logic without first dividing everything by 100 and using the following floating point arithmetic:
x + std::floor((y - x) * .5 * 100 + .5)*0.01
In other words, how can I do the above without floating point values but obtain the same behavior at the resolution of 100 instead of 0.01?
To compute the average you can do
avg = (x + y) / 2
(BTW, integer addition and division by 2 are very cheap operations even on small microcontrollers.)
To round this to the nearest multiple of 100 (corresponding to your floating-point example) you can do
result = ((avg + 50) / 100) * 100
as integer division rounds down to the nearest integer. By changing the 50 to 0 you can always round down, while changing it to 99 always rounds up.
Edit: Note that this method for rounding doesn't work for negative numbers. Since integer division rounds towards zero, in that case you'll need to subtract the 50, subtract 99 to always round down and subtract 0 to always round up.
Your problematic example requires strong conditions:
the difference between x and y needs to be not greater than 100
y % 100 must be 0
So for most cases, a simple rounded average is perfect for you:
avg100 = avg - (avg % 100) + 100
The tricky part is fixing the remaining error without a condition - if you want to avoid conditions, or slow operations.
For this, the best way is to use a multiplication, and split the expression into two:
avg100 = avg - (avg % 100)
avg100 += 100 * !!(y - avg100)
For most cases, y is greater than avg100. For this case, the !! operator will return 1. In the rare case when they equal, it will return a 0, and it won't change the value.
(I don't know if the compiler will really generate a code without conditions for the '!!' operator, but I don't have a batter idea, and if it is possible, I think it will. If not, this code is still short and easy to understand.)
Also, you can calculate the average using the following expression:
avg = y - (y-x)/2
Or even change the division into bit shift for optimization.
This won't require for both of the numbers to be even, just to be the same parity.
I am trying to implement a simple decimation algorithm in c++. I have two arrays, say p & q, where the subscripts are related to each other by the following relation:
p[k] = q[0.5*k]. This means that the following sequence should hold valid:
p[0] = q[0]
p[1] = 0
p[2] = q[1]
p[3] = 0
p[4] = q[2]
and so on...
Please note that p[k] takes on a value only and only when the result of (0.5*k) contains no decimal places (or has 0 in decimal) and does not use any rounding off etc.
My question is: Is there a way to distinguish between an integer (a number with no decimal places or only 0 in decimal, say 2.0) and a number with decimal places in C++, provided both are cast to double?
eg.) 2.0 is an integer cast to double. 2.1 is a number with decimal places.
eg. 2) * 0.9*2 should put 0 into array p while 0.9*10 should put q[9] into array p.*
If I use the statement, (int) (0.5*k), then I end up with an integer in every case, irrespective of the value of k.
Edit: The 0.5 in the above case is only illustrative. It could be any number, say 2, 2.5, 0.9, 0.95 etc.)
Any help is most welcome,
Thanks,
Sriram.
Assuming k is of an integer type, you could use if (k % 2 == 0) ... to check if kis divisible by two:
if (k % 2 == 0)
p[k] = q[k / 2];
else
p[k] = 0;
This can also be expressed using the ternary operator:
p[k] = (k % 2 == 0) ? q[k / 2] : 0;
Presuming that the coef can be anything else,
p[floor(coef*k)] = (fabs(coef*k-floor(coef*k))<1E-6)?q[k]:0;
The short syntax for what you want to do could be this:
p[k] = k % 2 ? 0 : q[k/2];
Is there a way to distinguish between a whole number and an integer in C++?
Define whole number, and define integer in this context. I'm confused!
Are you taking about the difference as explained here?
If you want to detect whether a number is integer or not, then probably this may help:
#include<cmath>
bool IsInteger(double d)
{
double intpart;
return std::modf(double number, &intpart) == 0.0;
}
k % 2 is in a couple of answers in this thread.
However, this is not useful in answering the OP's question. Note the edit:
"Edit: The 0.5 in the above case is only illustrative. It could be any number, say 2, 2.5, 0.9, 0.95 etc.)"
k % 2 only works because the value chosen was 0.5. It won't hold true for any other values.
Therefore, unless I'm missing something entirely, the simplest approach I can think of is the following:
Subtract the floor of the number from the number itself. If the result is > 0, it is not an integer.
Unless you have expressions that result in irrational numbers, you could use Boost.Rational to represent your indizes.
#Aix's suggestion of k%2 looks like it'd combine nicely with the ?: operator:
p[k] = (k%2) ? 0 : q[k/2];
Why is the output of the following code equals to 0 or serven?
cout << 7/9*9; //output 0 (zero) why?
float nine = 9;
float seven = 7;
float i = seven/nine*nine;
cout << i //output 7 Why?
Thanks for the help.
7/9*9 evaluates those numbers as integers, so 7/9 evaluates to 0, and 0*9 = 0.
When you made them floats, you were performing the intended calculation.
Try 7.0/9*9 to get 7, and then you'll be doing a floating point operation.
In C, when you divide integers, the remainder gets discarded. Here, you're doing 7 / 9, then taking the result of that and multiplying by 9. In steps, heres what C thinks:
7 / 9 = 0
0 * 9 = 0
When you use floats it works properly because the remainder is no longer discarded.
In:
cout << 7 / 9 * 9;
you are doing integer arithmetic. So 7/9 is 0 and 0*9 is 0.
To use floating point arithmetic (which is what you are using in your second example), you want to do:
cout << 7.0 / 9 * 9;
7/9*9 equals (7 / 9) * 9, but as 7 and 9 are integers and not floating point numbers, 7 / 9 equals 0 (the quotient of the division).
I think it's a precision issue. The / and * operators are equal precedence, so 7/9*9 is evaluated left to right at as (7/9)*9. The catch is that (7/9) is 0 in integer arithmetic. When you explicity store them as floats, that / operation is done in floating point, which can store 7/9 with greater precision than an int.
If you want to do the calculation in one line without the precision issue, try:
cout << 7.0f / 9.0f * 9.0f;
Many correct answers already. An addition note: if you want to leave this as an integer operation and not use floating point, you want to order it so you do multiplies before divides to get the most precision (as long as overflow doesn't occur during multiplication. Thus rather than (7.0/9)*9 which will convert to floats, you can do (9*7)/9.
The problem is to derive a formula for determining number of digits a given decimal number could have in a given base.
For example: The decimal number 100006 can be represented by 17,11,9,8,7,6,8 digits in bases 2,3,4,5,6,7,8 respectively.
Well the formula I derived so far is like this : (log10(num) /log10(base)) + 1.
in C/C++ I used this formula to compute the above given results.
long long int size = ((double)log10(num) / (double)log10(base)) + 1.0;
But sadly the formula is not giving correct answer is some cases,like these :
Number 8 in base 2 : 1,0,0,0
Number of digits: 4
Formula returned: 3
Number 64 in base 2 : 1,0,0,0,0,0,0
Number of digits: 7
Formula returned: 6
Number 64 in base 4 : 1,0,0,0
Number of digits: 4
Formula returned: 3
Number 125 in base 5 : 1,0,0,0
Number of digits: 4
Formula returned: 3
Number 128 in base 2 : 1,0,0,0,0,0,0,0
Number of digits: 8
Formula returned: 7
Number 216 in base 6 : 1,0,0,0
Number of digits: 4
Formula returned: 3
Number 243 in base 3 : 1,0,0,0,0,0
Number of digits: 6
Formula returned: 5
Number 343 in base 7 : 1,0,0,0
Number of digits: 4
Formula returned: 3
So the error is by 1 digit.I just want somebody to help me to correct the formula so that it work for every possible cases.
Edit : As per the input specification I have to deal with cases like 10000000000, i.e 10^10,I don't think log10() in either C/C++ can handle such cases ? So any other procedure/formula for this problem will be highly appreciated.
There are fast floating operations in your compiler settings. You need precise floation operations. The thing is that log10(8)/log10(2) is always 3 in math. But may be your result is 2.99999, for expample. It is bad. You must add small additive, but not 0.5. It should be about .00001 or something like that.
Almost true formula:
int size = static_cast<int>((log10((double)num) / log10((double)base)) + 1.00000001);
Really true solution
You should check the result of your formula. Compexity is O(log log n) or O(log result)!
int fast_power(int base, int s)
{
int res = 1;
while (s) {
if (s%2) {
res*=base;
s--;
} else {
s/=2;
base*=base;
}
}
return res;
}
int digits_size(int n, int base)
{
int s = int(log10(1.0*n)/log10(1.0*base)) + 1;
return fast_power(base, s) > n ? s : s+1;
}
This check is better than Brute-force test with base multiplications.
Either of the following will work:
>>> from math import *
>>> def digits(n, b=10):
... return int(1 + floor(log(n, b))) if n else 1
...
>>> def digits(n, b=10):
... return int(ceil(log(n + 1, b))) if n else 1
...
The first version is explained at mathpath.org. In the second version the + 1 is necessary to yield the correct answer for any number n that is the smallest number with d digits in base b. That is, those numbers which are written 10...0 in base b. Observe that input 0 must be treated as a special case.
Decimal examples:
>>> digits(1)
1
>>> digits(9)
1
>>> digits(10)
2
>>> digits(99)
2
>>> digits(100)
3
Binary:
>>> digits(1, 2)
1
>>> digits(2, 2)
2
>>> digits(3, 2)
2
>>> digits(4, 2)
3
>>> digits(1027, 2)
11
Edit: The OP states that the log solution may not work for large inputs. I don't know about that, but if so, the following code should not break down, because it uses integer arithmetic only (this time in C):
unsigned int
digits(unsigned long long n, unsigned long long b)
{
unsigned int d = 0;
while (d++, n /= b);
return d;
}
This code will probably be less efficient. And yes, it was written for maximum obscurity points. It simply uses the observation that every number has at least one digit, and that every divison by b which does not yield 0 implies the existence of an additional digit. A more readable version is the following:
unsigned int
digits(unsigned long long n, unsigned long long b)
{
unsigned int d = 1;
while (n /= b) {
d++;
}
return d;
}
Number of digits of a numeral in a given base
Since your formula is correct (I just tried it), I would think that it's a rounding error in your division, causing the number to be just slightly less than the integer value it should be. So when you truncate to an integer, you lose 1. Try adding an additional 0.5 to your final value (so that truncating is actually a round operation).
What you want is ceiling ( = smallest integer not greater than) logb (n+1), rather than what you're calculating right now, floor(1+logb(n)).
You might try:
int digits = (int) ceil( log((double)(n+1)) / log((double)base) );
As others have pointed out, you have rounding error, but the proposed solutions simply move the danger zone or make it smaller, they don't eliminate it. If your numbers are integers then you can verify -- using integer arithmetic -- that one power of the base is less than or equal to your number, and the next is above it (the first power is the number of digits). But if you use floating point arithmetic anywhere in the chain then you will be vulnerable to error (unless your base is a power of two, and maybe even then).
EDIT:
Here is crude but effective solution in integer arithmetic. If your integer classes can hold numbers as big as base*number, this will give the correct answer.
size = 0, k = 1;
while(k<=num)
{
k *= base;
size += 1;
}
Using your formula,
log(8)/log(2) + 1 = 4
the problem is in the precision of the logarithm calculation. Using
ceil(log(n+1)/log(b))
ought to resolve that problem. This isn't quite the same as
ceil(log(n)/log(b))
because this gives the answer 3 for n=8 b=2, nor is it the same as
log(n+1)/log(b) + 1
because this gives the answer 4 for n=7 b=2 (when calculated to full precision).
I actually get some curious resulting implementing and compiling the first form with g++:
double n = double(atoi(argv[1]));
double b = double(atoi(argv[2]));
int i = int(std::log(n)/std::log(b) + 1.0);
fails (IE gives the answer 3), while,
double v = std::log(n)/std::log(b) + 1.0;
int i = int(v);
succeeds (gives the answer 4). Looking at it some more I think a third form
ceil(log(n+0.5)/log(b))
would be more stable, because it avoids the "critical" case when n (or n+1 for the second form) is an integer power of b (for integer values of n).
It may be beneficial to wrap a rounding function (e.g. + 0.5) into your code somewhere: it's quite likely that the division is producing (e.g.) 2.99989787, to which 1.0 is added, giving 3.99989787 and when that's converted to an int, it gives 3.
Looks like the formula is right to me:
Number 8 in base 2 : 1,0,0,0
Number of digits: 4
Formula returned: 3
log10(8) = 0.903089
log10(2) = 0.301029
Division => 3
+1 => 4
So it's definitely just a rounding error.
Floating point rounding issues.
log10(216) / log10(6) = 2.9999999999999996
But you cannot add 0.5 as suggested, because it would not work for the following
log10(1295) = log10(6) = 3.9995691928566091 // 5, 5, 5, 5
log10(1296) = log10(6) = 4.0 // 1, 0, 0, 0, 0
Maybe using the log(value, base) function would avoid these rounding errors.
I think that the only way to get the rounding error eliminated without producing other errors is to use or implement integer logarithms.
Here is a solution in bash:
% digits() { echo $1 $2 opq | dc | sed 's/ .//g;s/.//' | wc -c; }
% digits 10000000000 42
7
static int numInBase(int num, int theBase)
{
if(num == 0) return 0;
if (num == theBase) return 1;
return 1 + numInBase(num/theBase,theBase);
}