If condition issue (C++) - c++

I have an issue with a piece of code in which I have an if statement that checks the diagonal elements of a complex array, and if they are (1,0) (meaning the real part is 1 and the imaginary part is 0) or very close to it then proceed; otherwise stop. But for some reason the operation always returns 0 although the elements are (0.999999, 0.000000), (1.000001, 0.000000), etc.
Here's the code I have:
for (i=1; i<=n; i++){
if ((real(c[i][i][1]) < (1/100000)+1) && (imag(c[i][i][1]) < 1/100000) && (real(c[i][i][1]) > (-1/100000+1) && (imag(c[i][i][1]) > -1/100000)){
cout<<"Operation continues...";
}
else
return 0;
}
Thanks in advance.

This integer division yields 0 because the magnitude of the denominator is greater than that of the numerator:
1/100000
You need to use at least one floating point number here. For example
1.0/100000

1 / 100000 == 0 as it is integer division:
you may write 0.00001 or 1. /100000.
BTW, you may write your loop:
constexpr double thresold = 0.00001;
for (i = 1; i <= n; i++) {
if (std::abs(real(c[i][i][1]) - 1.) < thresold
&& std::abs(imag(c[i][i][1]) - 1.) < thresold) {
cout << "Operation continues...";
}
else
return 0;
}

Related

C++) I don't know the fast algorithm to compare coordinates

Up to 100,000 coordinates are entered. Only coordinates corresponding to specific conditions should be output. If there are coordinates with larger x values ​​and smaller y values ​​than each coordinate, the corresponding coordinates are excluded from the output list.
My English is not good, so I'm giving some examples.
[input]
First enter the number of coordinates N to be input.
and enter the coordinates.
[output]
The coordinate numbers corresponding to the condition are output in ascending order.
[input example]
6
1 3
6 6
7 3
8 2
8 6
2 1
[output example]
4
5
6
coordinates image
The following problem was solved with a simple loop, but a timeout occurs when 100,000 values ​​are entered. I don't know which algorithm to use.
I also attach the C++ source code I wrote.
#include <iostream>
#include <algorithm>
#include <vector>
using namespace std;
int main() {
int N;
cin >> N;
bool* visible = new bool[N];
for (int i = 0; i < N; i++)visible[i] = true;
vector<pair<int,pair<int, int>>> v;
for (int i = 0; i < N; i++) {
int a, b;
cin >> a >> b;
v.push_back(make_pair(i,make_pair(a, b)));
}
for (int i = 0; i < v.size(); i++) {
if (visible[i] == false)
continue;
for (int j = 0; j < v.size(); j++) {
if (visible[i] == true &&visible[j]==true && v[i].second.first < v[j].second.first && v[i].second.second > v[j].second.second) {
visible[i] = false;
break;
}
else if (visible[i] == true && visible[j] == true && v[i].second.first > v[j].second.first && v[i].second.second < v[j].second.second) {
visible[j] = false;
continue;
}
}
}
for (int i = 0; i < v.size(); i++) {
if (visible[i] == true)
cout << v[i].first + 1 << endl;
}
return 0;
}
Looks like the problem about dominating points set.
Sort points by X value (Y is secondary key in case of X equality)
Assign the first point (with the largest X) to Big variable and add it to the result
Walk through array. If you meet point that is not dominated by Big - assign it to Big and add it to the result
The proper terms for your problem are Pareto front(ier), ND-tree, KD-tree, non-dominance problem.
There are libraries for that e.g.
https://github.com/alandefreitas/pareto-front
However it 2 dims it is a simple task.
You have to sort your points by one of the coordinates. And then scan from the best one to the worst and accepts only if the other coordinate is not dominated by previously acquired point. And it will give you O(n log(n)) that is the best possible in general case for such tasks.

add 1 to number represented by array of digits

The question goes as follows:
Given a non-negative number represented as an array of digits,
add 1 to the number ( increment the number represented by the digits ).
The digits are stored such that the most significant digit is at the head of the list.
Solution:
class Solution {
public:
vector<int> plusOne(vector<int> &digits) {
reverse(digits.begin(), digits.end());
vector<int> ans;
int carry = 1;
for (int i = 0; i < digits.size(); i++) {
int sum = digits[i] + carry;
ans.push_back(sum%10);
carry = sum / 10;
}
while (carry) {
ans.push_back(carry%10);
carry /= 10;
}
while (ans[ans.size() - 1] == 0 && ans.size() > 1) {
ans.pop_back();
}
reverse(ans.begin(), ans.end());
reverse(digits.begin(), digits.end());
return ans;
}
};
This is the solution i encountered while solving on a portal..
I cannot understand this :
while (ans[ans.size() - 1] == 0 && ans.size() > 1) {
ans.pop_back();
}
why do we need this while loop ? I tried self evaluating the code for example 9999 and i couldn't understand the logic behind popping the integers from the end!
Please help.
The logic
while (ans[ans.size() - 1] == 0 && ans.size() > 1) {
ans.pop_back();
}
removes any 0's at the end after incrementing the value by 1.
The logic is vague and isn't needed since you would never need ever find xyz..0000 in the answer set.
Example that the logic builder might have though: 9999 would be changed to 0000100 therefore he removes 0's to convert the conversion to 00001, which is reversed to form 10000, but since this scenario will never occur, the code should be removed from the logic.

Equal stacks:code not working for large input

I have been trying this since a long time but the code for the following problem is giving me wrong answer.
Problem Statement:You have three stacks of cylinders where each cylinder has the same diameter, but they may vary in height. You can change the height of a stack by removing and discarding its topmost cylinder any number of times.
Find the maximum possible height of the stacks such that all of the stacks are exactly the same height. This means you must remove zero or more cylinders from the top of zero or more of the three stacks until they're all the same height, then print the height. The removals must be performed in such a way as to maximize the height.
Explanation:
See this image: Explanation
Sample Input
5 3 4
3 2 1 1 1
4 3 2
1 1 4 1
Sample Output
5
My algorithm for this is:
Step I. get the 3 array and reverse them, create a new array out of an existing array with each element is sum of all the previous elements. eg: [3,2,1,1,1] -> [1,1,1,2,3] -> [1,2,3,5,8]
So the 3 new array formed would be [1,2,3,5,8] [2,5,9] [1,5,6,7]
Step II. Take the smallest array traverse the smallest array and search element in the other 2 array - if the element is existing in other 2 array, STOP there and return the number.
Eg. Here I start with element - 2 : Which is not existing in other 2 array. Next I start with element - 5 : it is existing in other 2 array.
My code:
#include<iostream>
using namespace std;
int main()
{
long long h1,h2,h3;
cin>>h1>>h2>>h3;
long long a[h1],b[h2],c[h3];
long long sum1=0,sum2=0,sum3=0;
for(long long i=0;i<h1;i++){
cin>>a[h1-i-1];
}
for(long long i=0;i<h2;i++){
cin>>b[h2-i-1];
}
for(long long i=0;i<h3;i++){
cin>>c[h3-i-1];
}
for(long long i=0;i<h1;i++){
sum1=sum1+a[i];
a[i]=sum1;
}
for(long long i=0;i<h2;i++){
sum2=sum2+b[i];
b[i]=sum2;
}
for(long long i=0;i<h3;i++){
sum3=sum3+c[i];
c[i]=sum3;
}
long long i = 0, j = 0, k = 0;
while (i < h1 && j < h2 && k < h3)
{
if (a[i] == b[j] && b[j] == c[k])
{ cout << a[i] << " "; return 0; }
else if (a[i] < b[j])
i++;
else if (b[j] < c[k])
j++;
else
k++;
}
cout<<0;
return 0;
}
What modification should I perform for the code to run for larger values of input?
This code gives wrong answer for some input.
Please help
You should traverse your array's in while loop from high to low values. Because we need highest value.Hence update your code
long long i = h1-1, j = h2-1, k = h3-1;
while (i >-1 && j > -1 && k >-1)
{
if (a[i] == b[j] && b[j] == c[k])
{ cout << a[i] << " "; return 0; }
else if (a[i] > b[j])
i--;
else if (b[j] > c[k])
j--;
else
k--;
}

Error trying to find all the prime numbers from 2 to n using Sieve of Eratosthenes in C++

I need to find all the prime numbers from 2 to n using the Sieve of Eratosthenes. I looked on Wikipedia(Sieve of Eratosthenes) to find out what the Sieve of Eratosthenes was, and it gave me this pseudocode:
Input: an integer n > 1
Let A be an array of Boolean values, indexed by integers 2 to n,
initially all set to true.
for i = 2, 3, 4, ..., not exceeding √n:
if A[i] is true:
for j = i2, i2+i, i2+2i, i2+3i, ..., not exceeding n :
A[j] := false
Output: all i such that A[i] is true.
So I used this and translated it to C++. It looks fine to me, but I have a couple errors. Firstly, if I input 2 or 3 into n, it says:
terminate called after throwing an instance of 'Range_error'
what(): Range_error: 2
Also, whenever I enter a 100 or anything else (4, 234, 149, 22, anything), it accepts the input for n, and doesn't do anything. Here is my C++ translation:
#include "std_lib_facilities.h"
int main()
{
/* this program will take in an input 'n' as the maximum value. Then it will calculate
all the prime numbers between 2 and n. It follows the Sieve of Eratosthenes with
the algorithms from Wikipedia's pseudocode translated by me into C++*/
int n;
cin >> n;
vector<string>A;
for(int i = 2; i <= n; ++i) // fills the whole table with "true" from 0 to n-2
A.push_back("true");
for(int i = 2; i <= sqrt(n); ++i)
{
i -= 2; // because I built the vector from 0 to n-2, i need to reflect that here.
if(A[i] == "true")
{
for(int j = pow(i, 2); j <= n; j += i)
{
A[j] = "false";
}
}
}
//print the prime numbers
for(int i = 2; i <= n; ++i)
{
if(A[i] == "true")
cout << i << '\n';
}
return 0;
}
The issue is coming from the fact that the indexes are not in line with the value they are representing, i.e., they are moved down by 2. By doing this operation, they no longer have the same mathematical properties.
Basically, the value 3 is at position 1 and the value 4 is at position 2. When you are testing for division, you are using the positions as they were values. So instead of testing if 4%3==0, you are testing that 2%1=0.
In order to make your program works, you have to remove the -2 shifting of the indexes:
int main()
{
int n;
cin >> n;
vector<string>A;
for(int i = 0; i <= n; ++i) // fills the whole table with "true" from 0 to n-2
A.push_back("true");
for(int i = 2; i <= sqrt(n); ++i)
{
if(A[i] == "true")
{
for(int j = pow(i, 2); j <= n; j += i)
{
A[j] = "false";
}
}
}
//print the prime numbers
for(int i = 2; i <= n; ++i)
{
if(A[i] == "true")
cout << i << '\n';
}
return 0;
}
I agree with other comments, you could use a vector of bools. And directly initialize them with the right size and value:
std::vector<bool> A(n, false);
Here you push back n-1 elements
vector<string>A;
for(int i = 2; i <= n; ++i) // fills the whole table with "true" from 0 to n-2
A.push_back("true");
but here you access your vector from A[2] to A[n].
//print the prime numbers
for(int i = 2; i <= n; ++i)
{
if(A[i] == "true")
cout << i << '\n';
}
A has elements at positions A[0] to A[n-2]. You might correct this defect by initializing your vector differently. For example as
vector<string> A(n+1, "true");
This creates a vector A with n+1 strings with default values "true" which can be accessed through A[0] to A[n]. With this your code should run, even if it has more deficits. But I think you learn most if you just try to successfully implement the sieve and then look for (good) alternatives in the internet.
This is painful. Why are you using a string array to store boolean values, and not, let's say, an array of boolean values? Why are you leaving out the first two array elements, forcing you to do some adjustment of all indices? Which you then forget half the time, totally breaking your code? At least you should change this line:
i -= 2; // because I built the vector from 0 to n-2, i need to reflect that here.
to:
i -= 2; // because I left the first two elements out, I that here.
// But only here, doing it everywhere is too annoying.
As a result of that design decision, when you execute this line:
for(int j = pow(i, 2); j <= n; j += i)
i is actually zero which means j will stay zero forever.

C++ Checking if a double is within .1 of another double (+/-)

I'm running a bit of code where I need to compare two 2D arrays for any variance. I've tried using the following line of code to check and compare the values, but the test fails every time = if(arr1[a][b] != arr2[a][b] || arr1[a][b] + .1 != arr2[a][b] || arr1[a][b] - .1 != arr2[a][b]) {.
I know this is failing because of the || statement, because one of the requirements is met. So I've got to find another way to determine if the double stored in a specific location in the array matches the other array in the parallel location.
Here's my full code:
int numberOfFailedCompares = 0;
for(int a = 0; a < 20; a++) {
int b = 0;
while(b < 20) {
if(arr1[a][b] != arr2[a][b] || arr1[a][b] + .1 != arr2[a][b] || arr1[a][b] - .1 != arr2[a][b]) {
numberOfFailedCompares++;
cout << numberOfFailedCompares << endl;
}
b++;
}
}
Is there a statement in C++ which will allow me to check if the value is within the +/- .1 threshold? Something like
if(arrLocation1 (+/- .1) == arrLocation1) {
...
}
"Variance" means "within X", and not "equal to something plus X or something minus X". Instead of comparing for equality, you compare for less/greater than your variance. So, for example, to test for variance of +/- .1:
if (b >= a-.1 && b <= a+.1)
How about this?
#define eps .1
...
if( fabs(x-y) <= eps )
...