programming g-adic expansion in c++ - c++

I want to program the g-adic expansion in the c++ language, but whatever I try, the output is still wrong. Let me first explain what the g-adic expansion is. The g-adic expansion is a way to represent numbers. For example, binary numbers, this is the 2-adic expansion of numbers. And hexadecimal is 16-adic expansion. So here is my code:
#include <iostream>
#include <cmath>
#include <complex>
#include <valarray>
using namespace std;
int main()
{
int x;
int g;
cin>>x;
cin>>g;
int k=log(x)/log(g)+1;
int e;
int b=0;
int* myArray=NULL;
myArray=new int[k];
for(int i=0;i<k;i++)
{
myArray[i]=0;
}
while(b!=k)
{
e=x/(g^(k-b-1));
myArray[b]=e;
x=x-e*g^(k-b-1);
b++;
}
b=0;
while(b!=k)
{
cout<<myArray[b]<<endl;
b++;
}
delete [] myArray;
myArray=NULL;
return 0;
}
So for example if I want to convert 105 to binary, x=105 and g=2, k is the length of the new number. In this case that is 7. int e=105/2^(7-1)=1. This is the first number. Then x=105-1*2^(7-1)=41. If you do this by hand, you will find that 105 becomes 1101001. But if I compile this piece of code, it just doesn't work. My question is what is wrong with this code?

The ^ doesn't do exponentiation. It's the exclusive-or operator. To do exponentiation, use the pow function.
e=x/std::pow(double(g),double(k-b-1));
myArray[b]=e;
x=x-e*std::pow(double(g),double(k-b-1));
You can see your program in action, with my changes, on IDE One.

here: run this program
#include <iostream.h>
#include <cmath>
#include<stdlib.h>
#include<stdio.h>
int main()
{
int x;
int g;
cin>>x;
cin>>g;
while(x>g)
{
cout<<x%g<<endl;
x/=g;
}
cout<<x%g<<endl;
return 0;
}
works for 105 and 2 and does not need an array

Related

A problem of ending the implementation of the code

this code works well for all samples, but after all samples are finished, a problem occurs. I don’t know what happens and the program crashes. Is there a problem with this code?
i have this problem when i use strings arrays usualy can it be the problem?
#include <iostream>
#include <vector>
#include <utility>
#include <algorithm>
#include <bits/stdc++.h>
#include <stdio.h>
#include <stdlib.h>
using namespace std;
long long t,n;
int a[1000];
string str[1000];
int main()
{
cin>>t;
for(int r=1;r<=t;r++){
cin>>n;
int maxi=0;
for(int i=1;i<=n;i++){
cin>>a[i];
if(a[i]>maxi)maxi=a[i];
};
//input first value
maxi=maxi+3;
for(int r1=0;r1<maxi;r1++){
str[1][r1]=(rand()%26)+'a';
}
for(int i=0;i<maxi;i++){
cout<<str[1][i];
}
cout<<endl;
//
for(int k=2;k<=(n+1);k++){
int w;
for(w=0 ; w<=a[k-1];w++){
str[k][w]=str[k-1][w];
};
for(int l=w-1;l<maxi;l++){
str[k][l]=(rand()%26)+'a';
};
for(int i=0;i<maxi;i++){
cout<<str[k][i];
}
cout<<endl;
}
}
return 0;
}
You are using elements of strings without allocating them.
Allocate elements by inserting
for(int i=1;i<=(n+1);i++){
str[i].resize(maxi);
}
just after
maxi=maxi+3;

How can I make code more time-efficient that calculates 1's in binary representation of int?

I wrote this code for a problem that asks me to calculate the number of 1's in a binary representation of an integer number, and then find the next number which has the same exact number of 1's in its binary number.
I wrote code and it seemed to work just fine until the OJ gives an error:
time limit exceeded error.
I'd like some idea about how I could avoid this error.
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
int binary(int num){
int count=0;
vector <int> vec;
while(num!=0){
int rem=num%2;
num/=2;
vec.push_back(rem);
}
reverse(vec.begin(),vec.end());
for(int i=0;i<vec.size();i++){
if(vec[i]==1){
count++;
}
}
return count;
}
int main()
{
int looper,order=1;
cin>>looper;
while(looper--){
int num;
cin>>num;
int x=binary(num);
int next_num=num+1;
while(binary(next_num)!=x){
next_num++;
}
cout<<"Case "<<order<<": "<<next_num<<endl;
order++;
}
return 0;
}
This:
int next_num=num+1;
while(binary(next_num)!=x){
next_num++;
}
Is extremely inefficient. Consider your number is
1010101.....01111
Then the next bigger number with same number of 1s is
1010101.....11110
I'll leave it to you to realize the general pattern, the point is just that you dont need a loop to convert all numbers to binary and count the 1s. Instead you can directly construct the number in binary.
PS: std::bitset can come in handy when you need to get the binary representation.
You don't need to count 1's if you're just finding next number that has same numbers of 1's
You just need to swap 1 & 0 from right to left for once.
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
int binary(int num){
int count=0;
vector <int> vec;
while(num!=0){
int rem=num%2;
num/=2;
vec.push_back(rem);
}
reverse(vec.begin(),vec.end());
for(int i=0;i<vec.size();i++){
while(vec[0]!=vec[i]){
swap(vec[0],vec[i]);
}
// convert binary to decimal
// count = decimal number
return count;
}
int main()
{
int looper,order=1;
cin>>looper;
while(looper--){
int num;
cin>>num;
int x=binary(num);
cout<<"Case "<<order<<": "<<x<<endl;
order++;
}
return 0;
}

Unexpected results converting decimal number to binary

# include <iostream>
# include <cmath>
using namespace std;
int main()
{
int p;
int n;
int q;
cin>>n;
int r;
r=0;
for (int i=0,n; n>1; i=i+1,n=n/2)
{
p=n%2;
q= p*(pow(10,i));
r=r + q;
}
cout<<r;
system("pause");
return 0;
}
I am not supposed to use arrays. It compiles fine but when executed and a number is entered, it doesn't produce the desired results.
For instance, when 22 is entered, it gives -2147483648 whereas the desired output would be 10110.
your way is limited and not effient in converting to binary
you should use string it's more helpful and the range is big enough for any number
this is my code for decimal-to-binary
#include<iostream>
#include<string>
#include<stack>
using namespace std;
int main()
{
long long n;
string s,bin;
stack<string> res;
cin>>n;
while(n>0)
{
if(n%2==0)
s='0';
else
s='1';
res.push(s);
n=n/2;
}
while(!res.empty())
{
bin=bin+res.top();
res.pop();
}
cout<<bin<<endl;
return 0;
}
I hope it will help you.
int i=0,n;
should be
int i=0;
I don't know what you thought you were doing there, but what you are actually doing is declaring another variable n. Because the second n variable doesn't have a value the rest of the code doesn't work.
That's not the only problem with your code, but I'm sure you can figure out the rest.

Why my code is giving wrong answer on SPOJ?

Problem: http://www.spoj.com/problems/TSORT/
Below code is giving correct output on my computer but it is giving wrong answer on spoj. I have tried this with several inputs and it is giving correct output. But still showing wrong answer on spoj.
#include<iostream>
#include<algorithm>
using namespace std;
int main()
{
int t;
cin>>t;
cin.tie(0);
ios::sync_with_stdio(false);
int *arr= new int[t];
for(int i=0;i<t;i++)
{
cin>>arr[i];
}
sort(arr,arr+t);
for(int i=0;i<t;i++)
{
cout<<"\n";
cout<<arr[i];
}
return 0;
}
As Tejas says, using cin and cout is not recommended in problems of optimization, as they are slower in comparison to scanf and printf. Extending his answer, you need to note that you use the STL sort that is slower than STL qsort. having this in mind, I tried your code with qsort and i got AC:
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstdlib>
using namespace std;
int a[1000008];
int compare (const void * a, const void * b)
{
return ( *(int*)a - *(int*)b );
}
int main()
{
int n,i;
scanf("%d",&n);
for(i=0;i<n;i++)
{
scanf("%d",&a[i]);
}
qsort(a,n,sizeof(int),compare);
for(i=0;i<n;i++)
printf("%d\n",a[i]);
return 0;
}
The int function compare is needed for the usage of qsort.
More info:
http://www.cplusplus.com/reference/cstdlib/qsort/
http://www.cplusplus.com/reference/algorithm/sort/
If you use cout<<arr[i]<<endl; it will give TLE instead of WA. So it means it has something to do with new line.
However if you want to get your answer accepted, you have to use printf and scanf instead of cin, cout. It is always suggested in such contests to use scanf and printf for reading large inputs.
I tried the following code and it was accepted
#include <iostream>
#include <cstdio>
#include <algorithm>
using namespace std;
int a[1000008];
int main()
{
int n,i;
scanf("%d",&n);
for(i=0;i<n;i++)
{
scanf("%d",&a[i]);
}
sort(a,a+n);
for(i=0;i<n;i++)
printf("%d\n",a[i]);
return 0;
}

Error when using 'int' datatype even when number is not a decimal

I understand the difference between int, float and double data types. But I have observed that sometimes when I use 'int' data type in a mathematical operation comprising of only integer values, it gives a result one less than the right answer. However, it's correct when I use float or double.
Take a look at the code below.
#include <iostream>
#include<math.h>
using namespace std;
int getno(int num)
{
int x,i;
float y=0;
for(i=0; i<4; i++)
{
x=num%10;
y=y+(x*pow(10,i));
num=num/10;
cout<<x*pow(10,i)<<endl;
cout<<y<<endl;
}
return y;
}
main()
{
int n;
cin>>n;
cout<<getno(n);
}
if I change the datatype of y to int, it gives a wrong answer by one. i.e 12345 would result in 2344 instead of the required 2345. Why is that happening?
I suppose "pow(10, i)" returns a bit less value than 10^i, let say 999.9999999 for i=3.
And afterwards it's truncated by float->int conversion into 99. As a result, we can loss 1 at every "y=.." operation.
I don't see your issue:
#include <iostream>
#include <math.h>
using namespace std;
int getno(int num)
{
int x,i;
float y=0;
for(i=0; i<4; i++)
{
x=num%10;
y=y+(x*pow(10.0f,(float)i));
num=num/10;
cout<<x*pow(10.0f,i)<<endl;
cout<<y<<endl;
}
return (int)y;
}
int main(void)
{
int n=12345;
// cin>>n;
cout<<getno(n);
return 0;
}
and the output is:
5
5
40
45
300
345
2000
2345
2345
I just cleaned up the warnings about int to float conversion on your call to pow and explicitly convert your return type.