c++学习笔记(2)
循环:
while循环 计数控制循环 counter-controlled loop
标记控制的循环: sentinel-conrolled loop
在写循环的过程中容易出现多一次或者少一次的错误 , 即差一错误 (off-by-one error)
计算减法--简单代码:
#include <iostream>
#include <cstdlib> // rand and srand function
#include <ctime> // for time function
using namespace std;
int main(int argc, char *argv[])
{
srand(time(0));
int number1 = rand() % 10;
int number2 = rand() % 10;
if(number1 < number2)
{
int temp = number1;
number1 = number2;
number2 = temp;
} // swap
cout << "What is " << number1 << " - " << number2 << " ? " << endl;
int answer;
cin >> answer;
while(answer != (number1 - number2))
{
cout << "You Entered a wrong answer !" << endl;
cout << "Enter again: ";
cin >> answer;
}
cout << "You git it!" << endl;
return 0;
}
猜数字:
先随机生成一个[0, 100]之间的整数,由用户数输入猜测数字,每次给出猜测的结果(偏大还是偏小,直到猜中为止)
#include <iostream>
#include <cstdlib> // rand and srand function
#include <ctime> // for time function
using namespace std;
int main(int argc, char *argv[])
{
srand(time(0));
int number = 0 + rand() % (100 - 0 + 1); // generate random number in [0, 100]
cout << "Enter your guess([0, 100]): ";
int guess;
cin >> guess;
while(guess != number)
{
if(guess - number > 0)
{
cout << "Your guess is too high." << endl;
}
else
{
cout << "Your guess is too low." << endl;
}
cout << "Enter your guess again: ";
cin >> guess;
}
cout << "Yes, the number is " << guess << "!" << endl;
return 0;
}
不要要浮点数作为循环的判断条件,因为浮点运算是一种近似的表示,程序可能会陷入死循环。
2.输入输出重定向
如果有许多数据需要输入,可以将文件存储在文件中,使用空格分开, 如input.txt,运行:
SentineValue.exe < input.txt 输入重定向命令, 从文件获取输入
输出重定向命令 SentineVAlue > output.txt , 可以将输出发送到文件中
输入输出重定向可以在同一个命令中:
SentineValue.exe < input.txt >output.txt
将input中的数据读取并发送到output中
(1)利用循环读取文件中的数据
#include <iostream>
#include <cstdlib> // rand and srand function
#include <ctime> // for time function
#include <fstream> // for file operation
using namespace std;
int main(int argc, char *argv[])
{
//srand(time(0));
ofstream output; // 先下入数据到txt文件中
output.open("number.txt");
for(int count=0; count<10; count++)
{
output << count << " ";
}
output << endl;
output << 3 << " " << 5 << endl;
output.close();
int number_1;
int sum=0;
// ifstream input("number.txt");
ifstream input;
input.open("number.txt");
while(!input.eof()) // eof()[end of file]测试是否读到了文件末尾
{
input >> number_1;
sum += number_1;
cout << number_1 << endl;
}
cout << "The sum is " << sum << endl;
return 0;
}
do-while 循环:while循环的变体
for 循环: 简洁
先验循环: while, for 循环, 循环的条件检验在循环体之前进行
后验循环: do while循环
#include <iostream>
#include <cstdlib> // rand and srand function
#include <ctime> // for time function
#include <fstream> // for file operation
#include <iomanip> // format outpit
using namespace std;
int main(int argc, char *argv[])
{
//srand(time(0));
cout << " Multiplication Table " << endl;
cout << " 1 2 3 4 5 6 7 8 9" << endl;
cout << "---------------------------------" << endl;
for(int i=1; i<= 10; i++)
{
cout << i << " | ";
for(int j=1; j<=10; j++)
{
cout << setw(3) << j*i << " ";
}
cout << endl;
}
return 0;
}
运行结果:
求最大公约数
#include <iostream>
#include <cstdlib> // rand and srand function
#include <ctime> // for time function
#include <fstream> // for file operation
#include <iomanip> // for foemat output
using namespace std;
int main(int argc, char *argv[])
{
//srand(time(0));
cout << "Enter a int number: ";
int number1;
cin >> number1;
cout << "Enter another number: ";
int number2;
cin >> number2;
int gcd = 1;
int k = 2; // 2-n1 2-n2
while(k<number1 && k<number2)
{
if(number1%k==0 && number2%k==0)
{
gcd = k;
}
k++;
}
cout << "The gcd is "<< gcd << endl;
return 0;
}
求最大公约数的其他方法:欧几里德算法,辗转相除法
欧几里德算法:
假设:
定义:
x % y =b, 则有b<y成立。
x = a*y +b ---> b = x - a*y,则x,y的最大公约数也是b的约数,此时令x=y, y=b, 重复上述步骤,
知道x%y=0时, 此时的y就是x, y的最大公约数(相当于不断缩小公约数的范围)
code:
#include <iostream>
#include <cstdlib> // rand and srand function
#include <ctime> // for time function
#include <fstream> // for file operation
#include <iomanip> // for foemat output
using namespace std;
int main(int argc, char *argv[])
{
// 欧几里得法求最大公约数
cout << "Enter a number1: ";
int x;
cin >> x;
cout << "Enter another number: ";
int y;
cin >> y;
if(x<y)
{
int temp;
temp = x;
x = y;
y = temp;
}
cout << "x = " << x << endl;
cout << "y = " << y << endl;
while(x%y != 0)
{
int b = x % y;
x = y;
y = b;
}
cout << "The gcd is " << y << endl;
return 0;
}
预测未来的学费:
假设初始的学费为¥10000, 每年以7%递增,多少年后学费会翻倍。
#include <iostream>
#include <cstdlib> // rand and srand function
#include <ctime> // for time function
#include <fstream> // for file operation
#include <iomanip> // for foemat output
#include <cmath> // for general math function
using namespace std;
int main(int argc, char *argv[])
{
float init_tuition = 10000; // 初始学费
float increase_rate = 0.07;
int year=1;
float tuition = init_tuition * pow((1+increase_rate), year);
while(tuition < 2*init_tuition)
{
year++;
tuition = init_tuition * pow((1+increase_rate), year);
}
cout << "After " << year << " year(s) " << " the tuition double" << endl;
return 0;
}
蒙特卡洛模拟:
估计pi的值,作边长为1的正方形和它的内切圆。
#include <iostream>
#include <cstdlib> // rand and srand function
#include <ctime> // for time function
#include <fstream> // for file operation
#include <iomanip> // for foemat output
#include <cmath> // for general math function
using namespace std;
const float RAND_MAX_float = static_cast<float>(RAND_MAX);
int main(int argc, char *argv[])
{
const int trial_nums = 100000;
int number_of_hits = 0;
srand(time(0));
for(int i=0; i<trial_nums; i++)
{
double x = rand() / RAND_MAX_float;
double y = rand() / RAND_MAX_float;
if(sqrt(x*x + y*y)<1)
{
number_of_hits++;
}
}
cout << "PI is " << 4.0 * number_of_hits / trial_nums << endl;
return 0;
}
十进制数转换转换为十六进制:
十进制数连续除以16,直到商为零。
总结: 将得到的字符串连接按照反序输出的方法:
code:
#include <iostream>
#include <cstdlib> // rand and srand function
#include <ctime> // for time function
#include <fstream> // for file operation
#include <iomanip> // for foemat output
#include <cmath> // for general math function
#include <string>
using namespace std;
const float RAND_MAX_float = static_cast<float>(RAND_MAX);
int main(int argc, char *argv[])
{
// decimal convert to
cout << "Enter a int: " << endl;
int decimal;
cin >> decimal;
int tmp = decimal;
string hex="";
char hex_char;
while(decimal!=0)
{
int hexValue = decimal % 16;
hex_char = (hexValue>=0 && hexValue<=9)?static_cast<char>(hexValue+'0'): static_cast<char>(hexValue-10+'A');
//hex = hex + hex_char; // 这种写法输出的顺序是反的
hex = hex_char +hex; // 这种写法的输出是正确的
decimal = decimal / 16;
}
cout << tmp << " to hex is " << hex << endl;
return 0;
}
输出素数
#include <iostream>
#include <string>
#include <iomanip>
using namespace std;
const int number_of_prime = 50;
const int number_of_prime_per_line = 10;
int main(int argc, char *argv[])
{
// 输出素数
int counter = 0;
int number = 2; // 素数起始
cout << "The first 50 primes are: " << endl;
while(counter < number_of_prime)
{
bool isPrime = true;
for(int devisor=2; devisor<=number/2; devisor++)
{
if(number % devisor == 0)
{
isPrime = false;
break;
}
}
if(isPrime)
{
counter++;
if(counter%number_of_prime_per_line==0)
{
cout << setw(4) << number << endl;
}
else
{
cout << setw(4) << number; // 固定宽度输出,不用考虑添加空格
}
}
number++;
}
return 0;
}