Objective
Programming using basic data types and control structures.
Specification
Write a program which converts a base-S floating point number with value in the range [0,1) to its equivalent base-D representation, where S, D =2, … , 10.
You program should be able to convert an input number with at least 8 significant digits而且.
Hint: Use input/output manipulators std::setw, std::setfill, and std::setprecision to format the output.
Sample run
Base conversion for numbers [0,1) with at least 8 significant digits.
Convert a number from base-S to base-D (2<=S<=10, 2<=D<=10):
Input S: 4
Input D: 9
Input a number [0,1)in base-4: 0.12341234
Error: 0.12341234 is an invalid base-4 number
Input a valid base-4 number: 0.12301230
0.12301230(4) is equivalent to 0.42352295(10) & 0.37266541(9)
Process another Conversion or Quit? (C/Q) C
Convert a number from base-S to base-D (2<=S<=10, 2<=D<=10):
Input S: 8
Input D: 5
Input a number in base-8: 0.66666666
0.66666666(8) is equivalent to 0.85714281(10) & 0.41203241(5)
Process another Conversion or Quit? (C/Q) Q
Note:
Ÿ Download the grade sheet as the cover page of your homework report.
Ÿ You may check the base converter for the assessment of your results.
intn=-1;// the power of n
doublebase10=0;// copy convert1
// Continuously taking decimal places
// convert to base-10
for(inti=0;i<significant;i++){number*=10;*convert1+=(int)number*pow(S,n);// e.g. 1.1 (base-2) -> 1*2^0 + 1*2^(-1) = 1.5 (base-10)
number-=(int)number;n-=1;}
base10=*convert1;// copy
n=-1;// init
// Continuously taking decimal places
// convert base-10 to base-D
/*
Because the precision of double is 16 ,
so multiply it by 17 and execute at least 17 times,
otherwise it will enter an infinite loop.
*/for(inti=0;i<17;i++){base10*=D;*convert2+=(int)base10*pow(10,n);base10-=(int)base10;n-=1;if(base10==0)// End early
{break;}}
在輸出時使用 API 提供的函式格式化。
1
cout<<setiosflags(ios::fixed)<<setprecision(8);
使用 GDB 進行調試,這樣能快速找到代碼問題。
Functions
int main() :主程序
double Scan(string, int *):輸入 string 的小數,轉換成 double 類型,並計算輸入小數的小數位數
#include<iostream>#include<math.h>#include<iomanip>#include<string>#include<stdlib.h>usingnamespacestd;doubleScan(string,int*);// count significant
boolisValid(double,int,int);// Judge the number's correctness (Base-S)
voidconvert(double,int,int,double*,double*,int);// convert the number from Base-S to Base-D and Base-10
intmain(){// initialize
doublenumber=0;// The number we need to input
intS=0;// base-S
intD=0;// base-D
charisQuit='C';// Judge whether to leave
doubleconvert1=0,convert2=0;// the result from convert()
stringcount;// The number we need to input
intsignificant=0;// the number's significant
// loop, if isQuit's value is 'Q',break it.
while(isQuit=='C'){// description
cout<<"Base conversion for numbers [0,1) with at least 8 significant digits.\n";cout<<"Convert a number from base-S to base-D (2<=S<=10, 2<=D<=10):\n";// input Base-S
cout<<"Input S: ";cin>>S;// input Base-D
cout<<"Input D: ";cin>>D;fflush(stdin);// loop
while(1){// input number
cout<<"Input a valid base-"<<S<<" number: ";// cin >> number;
number=Scan(count,&significant);if(isValid(number,S,significant))// number is valid
{break;}else// number is invalid
{cout<<"Error: "<<setiosflags(ios::fixed)<<setprecision(8)<<number<<" is an invalid base-"<<S<<" number\n";}}convert(number,S,D,&convert1,&convert2,significant);// convert
// output the result
cout<<setiosflags(ios::fixed)<<setprecision(8)<<number<<"("<<S<<") is equivalent to "<<convert1<<"(10) & "<<convert2<<"("<<D<<")"<<endl;// input isQuit
cout<<"Process another Conversion or Quit? (C/Q) -> ";cin>>isQuit;// Letters into uppercase
isQuit=toupper(isQuit);// initialize the values
convert1=0;convert2=0;significant=0;}system("pause");return0;}doubleScan(stringcount,int*significant){*significant=0;doublenumber=0;// we need to enter
intN=-1;cin>>count;// enter the string
fflush(stdin);for(inti=2;i<count.length();i++)// use count's length to loop
{*significant+=1;// count significant
number+=(count[i]-'0')*pow(10,N);// char -> double
N-=1;}returnnumber;}boolisValid(doublenumber,intS,intsignificant){doubleswapDouble=0;// Continuously taking decimal places
for(inti=0;i<significant;i++){number*=10;if((int)number>=S)// not meets Base-S
{returnfalse;// invalid
}else{swapDouble=(double)((int)number);number-=swapDouble;}}returntrue;// valid
}voidconvert(doublenumber,intS,intD,double*convert1,double*convert2,intsignificant){intn=-1;// the power of n
doublebase10=0;// copy convert1
// Continuously taking decimal places
// convert to base-10
/*
Reference
https://notfalse.net/17/positional-numeral-systems-conversion
*/for(inti=0;i<significant;i++){number*=10;*convert1+=(int)number*pow(S,n);// e.g. 1.1 (base-2) -> 1*2^0 + 1*2^(-1) = 1.5 (base-10)
number-=(int)number;n-=1;}base10=*convert1;// copy
n=-1;// init
// Continuously taking decimal places
// convert base-10 to base-D
/*
Because the precision of double is 16 ,
so multiply it by 17 and execute at least 17 times,
otherwise it will enter an infinite loop.
Reference
https://www.cnblogs.com/upzone/articles/1389365.html
*/for(inti=0;i<17;i++){base10*=D;*convert2+=(int)base10*pow(10,n);base10-=(int)base10;n-=1;if(base10==0)// End early
{break;}}}