感觉C++早晚是要学的,而且python做IEEE Xtreme动不动就time out且不易找到参考答案,故现在开始并以本文记录C++学习中的知识点。
起点: C++ 0基础
目标: 能够用C++做Leetcode
学习资料:
- C++ Primer 中文版(第 5 版)王刚,杨巨峰 译
- 学堂在线,清华大学, C++语言程序设计基础
根据学堂在线上的视频安装了Visual studio 2017作为IDE,并helloword;
学习C++ Primer 第一章 开始,重点总结:
内置类型 built-in type
如int类型就是一种内置类型
block of statements 语句块
{中间即为语句块}
输出运算符<<
左右两个对象,其中左侧的对象必须是一个ostream对象。<<将右侧的对象(一般是要打印的值)写入到左侧。,且结果是其左侧的运算对象。如:
std::cout << "Enter two numbers:" << std::endl;
等价于
(std::cout << "Enter two numbers:") << std::endl;
操纵符
操纵符是可以在 iostream 中插入或提取以起到特殊作用的值。
参数化操纵符是具有一个或多个参数的操纵符。
(见https://docs.oracle.com/cd/E19205-01/820-1214/bkall/index.html)
如上面代码中的enl是操纵符之一,它还执行了缓冲刷新操作。
注:打印类的语句应该保证”一直“刷新流
分号;
表示语句结束,如std::cout << "a";<<"and"<<std::endl; 就是不合法语句。
命名空间 name space
如std::cout中的std::指出名字cout是定义在名为std的命名空间中的。
作用域运算符 ::
作用域运算符用来指出想使用定义在命名空间中的名字。
输入运算符 >>
读入输入数据,左侧对象是一个istream对象,右侧是运算对象。它从给定的istream中读取数据并存入给定的对象中。与输出运算符类似,输入运算符返回左侧的运算对象作为计算结果。
Note:输出时运算对象可以不都是相同类型的值,如:
std::cout << "The sum of " << v1 << " and " << v2
<< " is " << v1 + v2 << std::endl;
其中,v1和v2等都是int类型。这是因为标准库定义了不同版本的输入输出运算符,来处理这些不同类型的运算对象。
这与python不同,如:
注释
//或/* blablabla */
注释不能嵌套
上述对应的程序为:
1.cpp
// ConsoleApplication1.cpp : This file contains the 'main' function. Program execution begins and ends there.
//
#include "pch.h"
#include <iostream>
using namespace std;
int main()
{
std::cout << "Enter two numbers:" << std::endl;
int v1 = 0;
int v2 = 0;
std::cin >> v1 >> v2;
std::cout << "The sum of " << v1 << " and " << v2
<< " is " << v1 + v2 << std::endl;
return 0;
}
// Run program: Ctrl + F5 or Debug > Start Without Debugging menu
// Debug program: F5 or Debug > Start Debugging menu
// /* hahaha */
//后面是非法注释 /* // */hahaha */
while语句
int main()
{
int sum = 0;
int val = 1;
while (val <= 10) {
sum += val; // sum = sum+val
++val; // val = val+1
}
std::cout << "Sum of 1 to 10 inclusive is " << sum << std::endl;
return 0;
}
其中,+=为复合赋值运算符; ++为前缀递增运算符。
注:Python中没有递增运算符++!python 中,变量是以内容为基准而不是像 c 中以变量名为基准,所以只要你的数字内容是5,不管你起什么名字,这个变量的 ID 是相同的,同时也就说明了 python 中一个变量可以以多个名称访问
>>> a = 5
>>> b = 5
>>> id(a)
1689021632
>>> id(b)
1689021632
>>> ++a
5
>>> id(a)
1689021632
>>> a++
File "<stdin>", line 1
a++
^
SyntaxError: invalid syntax
>>> a = a+1
>>> id(a)
1689021664
>>> a
6这样的设计逻辑决定了 python 中数字类型的值是不可变的,因为如果如上例,a 和 b 都是 5,当你改变了 a 时,b 也会跟着变,这当然不是我们希望的
因此,正确的自增操作应该 a = a + 1 或者 a += 1,当此 a 自增后,通过 id() 观察可知,id 值变化了,即 a 已经是新值的名称
1.4.1练习
/***********************************************************************************/
// ConsoleApplication1.cpp : This file contains the 'main' function. Program execution begins and ends there.
//
#include "pch.h"
#include <iostream>
using namespace std;
int main()
{
int val = 10;
while (val >= 0) {
std::cout << val << std::endl;
--val;
}
return 0;
}
/***********************************************************************************/
// ConsoleApplication1.cpp : This file contains the 'main' function. Program execution begins and ends there.
//
#include "pch.h"
#include <iostream>
using namespace std;
int main()
{
int start;
int end;
std::cout << "Please enter the start number";
std::cin >> start;
std::cout << "Please enter the end number";
std::cin >> end;
if (start > end)
std::cout << "Error! Start number should be greater that the end number. Enter again" << std::endl;
while (start <= end) {
std::cout << start << std::endl;
++start;
}
return 0;
}
for语句
for包含循环头和循环体。其中循环头包括3部分:初始化语句,循环条件和表达式。如
// ConsoleApplication1.cpp : This file contains the 'main' function. Program execution begins and ends there.
//
#include "pch.h"
#include <iostream>
using namespace std;
int main()
{
int sum = 0;
for (int val = 0; val <= 10; ++val)
sum += val;
std::cout << "the sum from 1 to 10 is " << sum << std::endl;
return 0;
}
/***********************************************************************************/
// ConsoleApplication1.cpp : This file contains the 'main' function. Program execution begins and ends there.
//
#include "pch.h"
#include <iostream>
using namespace std;
int main()
{
int start;
int end;
std::cout << "Please enter the start number: " << std::endl;
std::cin >> start;
std::cout << "Please enter the end number: " << std::endl;
std::cin >> end;
if (start > end) {
std::cout << "Error! The start number should be smaller than the end number" << std::endl;
return 0;
}
for (start; start <= end; ++start) {
std::cout << start << std::endl;
}
return 0;
}
读取数量不定的输入数据
当使用一个istream对象作为条件时,其效果是检测流的状态。如果流是有效的,即未遇到错误,则True;否则,当遇到文件结束符,或错误时,则返回False。如
// ConsoleApplication1.cpp : This file contains the 'main' function. Program execution begins and ends there.
//
#include "pch.h"
#include <iostream>
using namespace std;
int main()
{
int val = 0;
int sum = 0;
while (std::cin >> val) {
sum += val;
}
std::cout << "The sum of input numbers is " << sum << std::endl;
return 0;
}
if语句
// ConsoleApplication1.cpp : This file contains the 'main' function. Program execution begins and ends there.
//
#include "pch.h"
#include <iostream>
using namespace std;
// 统计输入中的每个值连续出现了多少次
int main()
{
int curval = 0;
int val = 0;
if (std::cin >> curval) { //第一个数
int cnt = 1; //计数
while (std::cin >> val) {
if (val == curval) {
++cnt;
}
else { //不等,则首先输出上一个字符的结果,之后开始下一个字符
std::cout << curval << " occurs " << cnt << " times." << std::endl;
curval = val;
cnt = 1;
}
}
// 打印最后一个数
std::cout << curval << " occurs " << cnt << " times." << std::endl;
}
return 0;
}
类简介
类类型:通过定义一个类Clss来定义自己的数据结构;
对象:可以通过定义类类型的变量来定义一个对象;
例如,通常将:“一个Sales_item类型的对象”简单说成“一个Sales_item对象”
成员函数/方法:成员函数是定义为类的一部分的函数,有时也被称为方法。
点运算符.
点运算符只能用于类类型的对象。左侧运算对象必须是一个类类型对象,右侧运算对象必须是该类型的一个成员名。运算结果为右侧运算对象指定的成员。例如item1.isbn()
调用运算符()
使用调用运算符来调用一个函数。调用运算符是().里面放实参数。
书店程序
std::cerr: cerr 是一个ostream对象,关联到标准错误,通常写入到与标准输出相同的设备。默认情况下,写到cerr的数据是不缓冲的。Cerr通常用于输出错误信息与其他不属于正常逻辑的输出内容。
详见: https://blog.csdn.net/liuhhaiffeng/article/details/52628561
要求:
程序应将每个ISBN的所有数据合并起来,存入名为total的变量。使用另一个名为trans的变量保存读取的每条销售记录。如果trans和total指向相同的ISBN,则更新total的值。否则,打印total的值,并将其重置为刚刚读取的数据(trans).
代码:
// ConsoleApplication1.cpp : This file contains the 'main' function. Program execution begins and ends there.
//
#include "pch.h"
#include <iostream>
#include "Sales_item.h"
读写Sales_item
//int main()
//{
// Sales_item book;
// // 读入ISBN、销售册数和销售价格
// std::cin >> book;
// // 写入ISBN\售出的册数、总销售额和平均价格
// std::cout << book << std::endl;
// return 0;
//}
Sales_item 对象的加法
//int main()
//{
// Sales_item item1, item2;
// std::cin >> item1 >> item2;
// // 首先检查是否有相同的ISBN
// if (item1.isbn() == item2.isbn()) {
// std::cout << item1 + item2 << std::endl;
// return 0; // yes
// }
// else {
// std::cerr << "Data must refer to same ISBN"
// << std::endl;
// return -1;
// }
//}
int main()
{
Sales_item total; //下一条交易记录的变量
// 读入并处理剩余交易记录, 从而确保有数据可以处理
if (std::cin >> total) {
Sales_item trans; // 保存和的变量
// 读入并处理剩余交易记录
while (std::cin >> trans) {
if (total.isbn() == trans.isbn()) {
total += trans; // 输入的trans和当前处理的total是同一本书, 则更新交易数据
}
else {
// 不是一本书,则先打打印前一本书的结果,再开始下一本书
std::cout << total << std::endl;
total = trans;
}
}
std::cout << total << std::endl; // 打印最后一本书的结果
return 0; //表示成功
}
else {
//没有输入,则输出警告
std::cerr << "No data?!" << std::endl;
return -1; // 表示失败
}
}
总结
这章主要就是熟悉C++,尤其是std::cout std::cin相关的知识。