#《Essential C++》读书笔记# 第一章 C++ 编程基础
前言
Stanley B.Lippman 先生所著的《C++ Primer》是学习C++的一本非常优秀的教科书,但《C++ Primer》作为一本大部头书,显然不适合所有的初学者。所以Lippman先生又返璞归真地写了这本短小轻薄的《Essentia C++》。这本书以简短的章节篇幅,帮助初学者快速学习C++的语法,了解C++语言特性,理解C++的设计目的和基本原理。笔者阅读的是《Essential C++》中文版,其译者为侯捷老师,他也是《C++ Primer》中文版第三版的译者。
基础知识
第一个完整的C++程序:
- #include <iostream>
- #include <string>
- using namespace std;
- int main()
- {
- string user_name;
- cout << "Please enter your first name:";
- cin >> user_name;
- cout << '\n'
- << "Hello, "
- << user_name
- << "...and goodbye!\n";
- return 0;
- }
关键字(keyword),就是程序语言预先定义的一些具有特殊意义的名称。
函数(function)是一块独立的程序代码序列,能够执行一些运算。它包含四个部分,返回值类型(return type),函数名称,参数列表(parameter list),以及函数体(function body)。main并非是程序语言定义的关键字,但是,C++编译系统会假设程序中定义有main()函数。main()函数是程序执行的起点,如果我们没有定义,程序将无法执行。
类(class),class机制赋予了我们“增加程序内之类型抽象化层次”的能力。class机制让我们得以将数据类型加入我们的程序中,并有能力识别它们。面向对象的类层次体系(class hierarchy)定义了整个家族体系的各个相关类型。class的定义一般来说分为两部分,分别写在不同的文件中。一个就是所谓的“头文件(header file)”,用来声明该class所提供的的各种操作行为(operation)。另一个文件,程序代码文件(program text),则包含了这些行为的实现内容(implementation)。欲使用class,我们必须先在程序中包含其头文件,头文件可以让程序知道class的定义。
命名空间(namespace),是一种将库名称封装起来的方法。通过这种方法,可以避免和应用程序发生命名冲突得到问题(所谓命名冲突是指在应用程序内两个不同的实体(entity)具有相同名称),导致程序无法区分两者。命名冲突发生时,程序必须等到该命名冲突获得解析(resolve)之后,才得以继续执行。命名空间像是在众多名称的可见围内竖起一道围墙。
为了定义对象,我们必须为它命名,并赋予它数据类型。对象名称可以是任何字母、数字、下画线的组合,并大小写敏感。对象名称不能以数字开头。当然任何命名不能和程序语言本身关键字完全一致。例如 delete 是语言关键字,所以 string class 采用 earse() 而非 delete() 来表示“删去一个字符”的原因。
template class 允许我们在“不必指明 data member 类型”的情况下定义class。template class 机制使程序员得以直到使用 template class 时才决定真正的数据类型。程序员可以先插入一个代名,稍后才绑定至实际的数据类型。
由于反斜线字符以用作转义字符的起头字符,因此连续两个反斜线即表示一个真正的反斜线字符。
被定义为 const 的对象,在获得初值之后,无法在有任何变动。如果你企图为 const 对象指定新值,会产生编译错误。
对于 OR 逻辑运算符( || ),左侧表达式会先被求值,如果其值为 true,剩下的表达式就不需要再被求值(此所谓短路求值法)。AND 逻辑运算符( && ),最左侧表达式会先被求值,其结果若为 false ,则 AND 运算符的求值结果即为 false,其余表达式不会再被求值。
一些运算符优先级简列于下,位置在上者的优先级高于位置在下者,同一行的各种运算符具有相同的优先级,其求值次序取决于它在该表达式中的位置(由左至右)。
逻辑运算符 NOT
算术运算符(*,/,%)
算术运算符(+,-)
关系运算符(<,>,<=,>=)
关系运算符(==,!=)
逻辑运算符 AND
逻辑运算符 OR
赋值运算符 (assignment = )
如果要访问一个由指针所指的对象,我们必须对该指针进行提领(dereference,也叫解引用)操作——也就是取得“位于该指针所指内存地址上”的对象。在指针之前使用“*”号,便可以达到这个目的。
我们可以使用 dot 成员选择运算符(member selection opereation),用来选择我们想要的操作。如果要通过指针来选择操作,必须改用 arrow 成员选择运算符。如果要使用下标运算符(subscript operator),我们必须先提领指针,由于下标运算符的优先级较高,因此指针提领操作的两旁必须加上小括号。
练习题答案
练习1.5 编写一个程序,能够询问用户的姓名,并读取用户所输入的内容。请确保用户输入的名称长度大于两个字符。如果用户的确输入了有效的名称,就响应一些信息。请以两种方式实现:第一种使用C-style字符串,第二种使用string对象。
- #include <iostream>
- #include <string>
- #include <iomanip>
- #include <cstring>
- using namespace std;
- #define MAX 50
- #define MIN 2
- int main()
- {
- //C-style 字符串
- /*
- const int nm_size = 128; //分配一个固定大小
- char user_name[nm_size];
- cout << "Please enter your name:";
- cin >> setw(nm_size) >> user_name; //保证读入不超过127个字符,最后一个空间保存null
- size_t len = strlen(user_name);
- if (len <= 3)
- {
- cout << "Please enter a longer name!" << endl;
- return 0;
- }
- cout << "Hello," << user_name << endl;
- */
- //string对象
- string user_name;
- cout << "Please enter your name:";
- cin >> user_name;
- size_t len = user_name.size(); //获取的即为字符串长度,无null
- if (len <= 2)
- {
- cout << "Please enter a longer name!" << endl;
- return 0;
- }
- cout << "Hello," << user_name << endl;
- return 0;
- }
练习1.6 编写一个程序,从标准输入设备读取一串整数,并将读入的整数依次放到 array 和 vector,然后遍历这两种容器,求取值总和。将总和及平均值输出至标准输出设备。
- #include <iostream>
- #include <vector>
- using namespace std;
- #define MAX 10
- int main()
- {
- /*
- //存放到vector
- vector<double> v;
- double temp=0;
- double sum = 0;
- double ave = 0.0;
- while (cin >> temp)
- {
- v.push_back(temp);
- }
- for (int i = 0;i < v.size();i++)
- {
- sum += v[i];
- }
- ave = sum / v.size();
- cout << "Sum=" << sum << endl;
- cout << "Average=" << ave << endl;
- */
- //存放到array
- double arr[MAX];
- int count = 0;
- int count2 = 0;
- double temp;
- double sum = 0.0;
- double ave = 0.0;
- while (count<10 && cin >> temp)
- {
- arr[count] = temp;
- count++;
- }
- count2 = count;
- count--;
- while (count >= 0)
- {
- sum += arr[count];
- count--;
- }
- ave = sum / count2;
- cout << "Sum=" << sum << endl;
- cout << "Average=" << ave << endl;
- return 0;
- }
练习1.7 使用你最称手的编辑工具,输入两行(或更多)文字存盘。然后编写一个程序,打开该文本文件,将其中的每个字都读取到一个 vector<string> 对象中。遍历该 vector,将内容显示到 cout。然后利用泛型算法 sort(),对所有文字排序。
- #include <iostream>
- #include <fstream>
- #include <algorithm>
- #include <string>
- #include <vector>
- using namespace std;
- int main()
- {
- ifstream in_file("1.txt");
- if (!in_file)
- {
- cerr << "opps! unable to open input file\n";
- return -1;
- }
- ofstream out_file("2.txt");
- if (!out_file)
- {
- cerr << "opps! unable to open output file\n";
- return -1;
- }
- string word;
- vector<string> text;
- while (in_file >> word)
- text.push_back(word);
- size_t ix;
- cout << "unsorted text:\n";
- for (ix = 0;ix < text.size();++ix)
- {
- cout << text[ix] << ' ';
- }
- cout << endl;
- sort(text.begin(), text.end());
- cout << "sorted text:\n";
- for (ix = 0;ix < text.size();++ix)
- {
- cout << text[ix] << ' ';
- out_file << text[ix] << ' ';
- }
- cout << endl;
- out_file << endl;
- return 0;
- }
练习1.8 1.4节的 switch 语句让我们得以根据用户答错的次数提供不同的安慰语句。请以 array 储存四种不同的字符串信息,并以用户答错的次数作为 array 的索引值,以此方式来显示安慰语句。
- #include <iostream>
- #include <stdlib.h>
- #include <ctime>
- using namespace std;
- const char* msg_to_usr(int num_tries);
- int main()
- {
- int count=0;
- srand(time(0));
- int answer = rand() % 3;
- int myAnswer;
- char isContinue = 'y';
- while (isContinue=='y')
- {
- cout << "Please input your answer(0-2): ";
- cin >> myAnswer;
- if (myAnswer == answer)
- {
- cout << "Congratulations!" << endl;
- break;
- }
- else
- {
- count++;
- cout << msg_to_usr(count) << endl;
- cout << "Continue? input y or n: ";
- cin >> isContinue;
- }
- }
- return 0;
- }
- const char* msg_to_usr(int num_tries)
- {
- const int rsp_cnt = 5;
- static const char* usr_msgs[rsp_cnt] =
- {
- "Go on, make a guess. ",
- "Oops! Nice guess but not quite it. ",
- "Hmm. Sorry. Wrong a second time. ",
- "Ah, this is harder than it looks, no? ",
- "It must be getting pretty frustrating by now! "
- };
- if (num_tries < 0)
- {
- num_tries = 0;
- }
- else if (num_tries >= rsp_cnt)
- num_tries = rsp_cnt - 1;
- return usr_msgs[num_tries];
- }
end。
“取乎其上,得乎其中;取乎其中,得乎其下;取乎其下,则无所得矣。”
#《Essential C++》读书笔记# 第一章 C++ 编程基础的更多相关文章
- 第一章 C++编程基础
第一章 C++编程基础 1.1 如何撰写C++程序 赋值 assignment复合赋值 (compound assignment) += 函数(function)是一块独立的程序代码序列(code s ...
- 《css3实战》读书笔记 第一章 基于CSS需求而编写的HTML.
笔记说明 <CSS3实战手册第3版(影印版)>可以消除Web设计工作的痛苦,并且带给你:HTML--重新入门.如果你是HTML新手,你会学到如何以CSS友好的方式进行基本页面构造.若你是H ...
- .net架构设计读书笔记--第一章 基础
第一章 基础 第一节 软件架构与软件架构师 简单的说软件架构即是为客户构建一个软件系统.架构师随便软件架构应运而生,架构师是一个角色. 2000年9月ANSI和IEEE发布了<密集性软件架构建 ...
- 《疯狂Java:突破程序员基本功的16课》读书笔记-第一章 数组与内存控制
很早以前就听过李刚老师的疯狂java系列很不错,所以最近找一本拿来拜读,再此做下读书笔记,促进更好的消化. 使用Java数组之前必须先对数组对象进行初始化.当数组的所有元素都被分配了合适的内存空间,并 ...
- Getting Started With Hazelcast 读书笔记(第一章)
第一章:数据集群的演化与 早期的服务器架构 显然,应用是可扩展的,但是由于是集中式服务器,随着数据库性能达到极限,再想扩展就变得极端困难,于是出现了缓存. 缓存显然再次提升了可扩展性,减轻了数据 ...
- C缺陷与陷阱----读书笔记---第一章
第一章:词法陷阱 编译器中负责将程序分解为一个一个符号的部分,一般称为“词法分析器”.例如,对于语句: if ( x == big ) big = x ; 它的第一个符号是C语言关键字if,紧接着下一 ...
- 《C++ Primer》读书笔记 第一章
读<C++ Primer>才知道,自己对C++知之甚少... 写个博客记录下自己C++的成长,只是读书笔记,不是对<C++ Primer>知识点的总结,而是对自己在书上看到的以 ...
- 《深入理解计算机系统》(CSAPP)读书笔记 —— 第一章 计算机系统漫游
本章通过跟踪hello程序的生命周期来开始对计算机系统进行学习.一个源程序从它被程序员创建开始,到在系统上运行,输出简单的消息,然后终止.我们将沿着这个程序的生命周期,简要地介绍一些逐步出现的关键概念 ...
- javascript 数据结构和算法读书笔记 > 第一章 javascript的编程环境和模型
1.变量的声明和初始化 必须使用关键字 var,后跟变量名,后面还可以跟一个赋值表达式. var name; var age = 5; var str = 'hello'; var flg = fal ...
随机推荐
- Spring-Cloud之Eureka注册中心环境搭建(单节点)
一 Eureka概述 服务启动时会生成服务的基本信息对象InstanceInfo,然后在启动时会register到服务治理中心. 注册完成后会从服务治理中心拉取所有的服务信息,缓存在本地. 之后服务会 ...
- Linux Centos7 在桌面添加快捷方式
当时,刚刚安装好centos7,又下载好了jb家的软件,但是每一次都要用命令行才能运 我想要的是下面的效果,那是我后来才研究出来的 我看到了自动生成的为什么可以用,我的打开了源文件研究了一下 第一,先 ...
- redis端口6379的由来
有一个技巧,Redis端口号6379,是手机键盘上的MERZ.
- (转)KL散度的理解
KL散度(KL divergence) 全称:Kullback-Leibler Divergence. 用途:比较两个概率分布的接近程度.在统计应用中,我们经常需要用一个简单的,近似的概率分布 f * ...
- DWZ框架--页面样式丢失
案例 今天我导入DWZ框架demo时,发现主页面样式丢失,出现了如下图那鬼样: 正常情况应该是有表格显示,并且用chrome开发者模式调试,可以看到有对应的样式,如下图所示: 先简单介绍下dwz框架的 ...
- Arduino系列之按键模块(一)
今天我将简单介绍按键模块计数的原理: 我们常用的按键及按键模块有2脚和4脚的,其内部结构如图所示,当按下按键时就会接通按键两端,当放开时,两端自然断开. ...
- 删除我的电脑wps、百度网盘图标
删除我的电脑wps.百度网盘图标 删除下面子项 输入"计算机\HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Expl ...
- 11、ACL
IP访问控制列表 标准ACL 1)检查源地址 2)不能对协议簇作限定 扩展ACL 1)检查源和目标地址 2)能容许或拒绝特定的协议和应用(端口号) 区别列表类型: 1)ACL号 : 1-99,1300 ...
- Spanner的TrueTime与事务
Spanner的TrueTime与事务 Spanner是谷歌的分布式数据库,发表于著名论文Spanner: Google's Globally-Distributed Database,它创造性的采用 ...
- Zabbix监控实现跨区域跨网络监控数据
Zabbix监控实现跨区域跨网络监控数据 环境: 公司现有服务器10台,其中5台服务器有一台安装了zabbix,并且这5台服务器处于一个网络,只有一台服务器有公网ip, 另外的5台处于另一个网络,仅有 ...