嵌入式技术
一、程序源文件命名约定
无论你使用命令行界面或者IDE,大多数编译器都要求程序源码存储在一个或多个文件中。程序文件通常被称为源文件(source file)。在大多数系统中,源文件的名字以一个后缀为结尾,后缀是由一个句点后接-一个或多个字符组成的。后缀告诉系统这个文件是一个C++程序。不同编译器使用不同的后缀命名约定,最常见的包括. cc、.cxx、.cpp、.cp及.C。
二、初识输入输出
本书中的很多示例都使用了iostream 库。iostream 库包含两个基础类型istream和ostream,分别表示输入流和输出流。一个流就是一个字符序列,是从IO设备读出或写入IO设备的。术语“流" (stream)想要表达的是,随着时间的推移,字符是顺序生成或消耗的。
#include < iostream > // 头文件
int main()
{
std::cout < < "Enter two numbers : " < < std::endl;
int v1 = 0, v2 = 0;
std::cin > > v1 > > v2 ;
std::cout< < "The sum of " < < v1 < < " and " < < v2 < < " is " < < v1 + v2 < < std::endl;
return 0;
}
这个程序开始时在用户屏幕打印
Enter two numbers :
然后等待用户输入。如果用户键入
6 8
然后键入一个回车,则程序产生如下输出:
The sum of 6 and 8 is 14
1、向流写入数据
main 的函数体的第一条语句执行了一个表达式(expression)。在C++中,一个表达式产生一个计算结果,它由一个或多个运算对象和(通常是) 一个运算符组成。这条语句中的表达式使用了输出运算符(<<)在标准输出上打印消息:
std::cout < < "Enter two numbers : " < < std::endl;
<< 运算符接受两个运算对象:左侧的运算对象必须是一个 ostream对象,右侧的运算对象是要打印的值。此运算符将给定的值写到给定的ostream对象中。输出运算符的计算结果就是其左侧运算对象。即,计算结果就是我们写入给定值的那个ostream对象。我们的输出语句使用了两次<<运算符。因为此运算符返回其左侧的运算对象,因此第一个运算符的结果成为了第二个运算符的左侧运算对象。这样,我们就可以将输出请求连接起来。
因此,我们的表达式等价于;
(std::cout << "Enter two numbers:") << std::endl;
等价于:
std: :cout << "Enter two numbers:";
std: :cout << std: :endl;
第一个输出运算符给用户打印一条消息。这个消息是一个字符串字面值常量(string literal),是用一对双引号包围的字符序列。在双引号之间的文本被打印到标准输出。
第二个运算符打印endl,这是一个被称为操纵符(manipulator)的特殊值。写入endl的效果是结束当前行,并将与设备关联的缓冲区( buffer)中的内容刷到设备中。缓冲刷新操作可以保证到目前为止程序所产生的所有输出都真正写入输出流中,而不是仅停留在内存中等待写入流。
2、使用标准库中的名字
细心的读者可能会注意到这个程序使用了std: :cout和std: :endl。前缀std: :指出名字cout和endl是定义在名为std的命名空间(namespace)中的。标准库定义的所有名字都在命名空间std中。通过命名空间使用标准库有一个副作用:当使用标准库中的一个名字时,必须显式说明我们想使用来自命名空间std中的名字。例如,需要写出std: :cout,通过使用作用域运算符( :: )来指出我们想使用定义在命名空间std中的名字cout。将给出一个更简单的访问标准库中名字的方法。
3、从流读取数据
在提示用户输入数据之后,接下来我们希望读入用户的输入。
std: :cin >> v1 >> v2;
它读入输入数据。输入运算符(>>)与输出运算符类似,它接受一个istream作为其左侧运算对象,接受一个对象作为其右侧运算对象。它从给定的istream 读入数据,并存入给定对象中。与输出运算符类似,输入运算符返回其左侧运算对象作为其计算结果。
因此,此表达式等价于(std: :cin >> v1) >> v2;
等价于:
std::cin >> v1;
std::cin>>v2;
三、注释简介
// 正确
/* 正确 */
/* 正确
*/
/*
★注释对/* */不 能嵌套。
★
“不能嵌套”几个字会被认为是源码,
★像剩余程序一样处理
*/
#include < iostream >
int main()
{
std ::cout < < "/*";
std ::cout < < "*/";
std ::cout < < /* "*/" */";
std ::cout < < /*"*/"/*"/*" */;
return 0;
}
四、控制流
语句一般是顺序执行的:语句块的第一条语句首先执行, 然后是第二条语句,依此类推。但程序设计语言提供了多种不同的控制流语句,允许我们写出更为复杂的执行路径。
1、while语句
C语言学习进阶~总贴
2、for语句
C语言学习进阶~总贴
3、读取数量不定的输人数据
在某种情况下,我们预先不知道要对多少个数求和,这就需要不断读取数据直至没有新的输入为止:
#include < iostream >
int main()
{
int sum = 0, value = 0;
std::cout < < "Enter " < < std::endl;
while (std::cin > > value) //读取数据直到遇到文件尾,计算所有读入的值的和
sum += value; //等价于sum=sum+value
std::cout < < "Sum is : " < < sum < < std::endl;
return 0;
}
如果我们输入.
3 4 5 6 7 8
则程序会输出
Sum is : 33
因此,我们的while 循环会一直执行 直至遇到文件结束符(或输入错误)。while循环体使用复合赋值运算符将当前值加到sum上。一旦条件失败,while循环将会结束。将执行下一条语句,打印sum的值和一个endl。
从键盘输入文件结束符
当从键盘向程序输入数据时,对于如何指出文件结束,不同操作系统有不同的约定。在Windows系统中,输入文件结束符的方法是敲Ctrl+Z (按住Ctrl 键的同时按Z键),然后按Enter或Return键。在UNIX系统中,包括MacOSX系统中,文件结束符输入是用Ctrl+D。
4、if 语句
与大多数语言一样,C++也提供了if语句来支持条件执行。我们可以用if语句写一个程序,来统计在输入中每个值连续出现了多少次:
#include < iostream >
int main()
{
// currVal 是我们正在统计的数; 我们将读入的新值存入val .
int currVal = 0, val = 0;
//读取第一个数,并确保确实有数据可以处理
if (std::cin > > currVal) {
int cnt = 1;
//保存我们正在处理的当前值的个数
while (std::cin > > val)
{ // 读取剩余的数
if (val == currVal) // 如果值相同
++cnt;
//将cnt加1
else
{
//否则,打印前一个值的个数
std::cout < < currVal < < " occurs "< < cnt < < " times" < < std::endl;
currVal = val;
//记住新值
cnt = 1;
//重置计数器
} // while循环在这里结束
//记住打印文件中最后一个值的个数
}
std::cout < < currVal < < " occurs " < < cnt < < " times" < < std::endl;
}//最外层的if语句在这里结束
return 0;
}
5、类简介
在C++中,我们通过定义一个类(class) 来定义自己的数据结构。一个类定义了一个类型,以及与其关联的一组操作。类机制是C++最重要的特性之一。实际上,C++最初的一个设计焦点就是能定义使用上像内置类型一样自然的类类型(class type)。
为了使用类,我们需要了解三件事情:
Sales item item;
是想表达item是一个Sales_ item 类型的对象。
(1)读写Sales_ item
#include < iostream >
#include "Sales_item.h"
int main()
{
Sales_item book;
//读入ISBN号、售出的册数以及销售价格.
std:: cin > > book;
//写入ISBN、 售出的册数、总销售额和平均价格
std:: cout < < book < < std:: endl;
return 0;
}
如果输入:
0-201-70353-X 4 24.99
则输出为:
0-201-70353-x 4 99.96 24.99
(2)Sales_ item对象的加法
#include < iostream >
#include "Sales_ item.h"
int main()
{
Sales_item item1,item2;
std:: cin > > iteml > > item2;
//读取一对交易记录
std:: cout < < item1 + item2 < < std :: endl;
//打印它们的和
return 0;
}
如果输入如下内容:
0-201-78345-X 3 20. 00
0-201-78345-x 2 25.00
则输出为:
0-201-78345-X 5 110 22
(3)初识成员函数
将两个Sales_item对象相加的程序首先应该检查两个对象是否具有相同的ISBN。
方法如下:
#include < iostream >
#include "Sales item.h"
int main()
{
Sales_item iteml, item2;
std::cin > > iteml > > item2;
//首先检查item1和item2是否表示相同的书
if (iteml.isbn() == item2.isbn()) {
std::cout < < item1 + item2 < < std::endl;
return 0; // 表示成功
}
else {
std::cerr < < "Data must refer to same ISBN" < < std :: endl;
return -1;
//表示失败
}
}
什么是成员函数?
这个if语句的检测条件 item1. isbn() == item2.isbn()
调用名为isbn的成员函数(member function)。成员函数是定义为类的一部分的函数,有时也被称为方法(method)。我们通常以一个类对象的名义来调用成员函数。
使用点运算符(.)来表达我们需要“名为item1的对象的isbn成员”。点运算符只能用于类类型的对象。其左侧运算对象必须是一个类类型的对象,右侧运算对象必须是该类型的一个成员名,运算结果为右侧运算对象指定的成员。
6、书店程序
我们需要从一个文件中读取销售记录,生成每本书的销售报告,显示售出册数、总销售额和平均售价。我们假定每个ISBN书号的所有销售记录在文件中是聚在一起保存的。
我们的程序会将每个ISBN的所有数据合并起来,存入名为total的变量中。我们使用另一-个名为trans的变量保存读取的每条销售记录。如果trans和total指向相同的ISBN,我们会更新total的值。否则,我们会打印total的值,并将其重置为刚刚读取的数据(trans):
#include < iostream >
#include "Sales item. h"
int main()
{
Sales_item total; // 保存下一条交易记录的变量
//读入第一条交易记录,并确保有数据可以处理
if (std:: cin > > total)
{
Sales_item trans;
//保存和的变量
//读入并处理剩余交易记录
while (std:: cin > > trans)
{
//如果我们仍在处理相同的书
if (total.isbn() == trans.isbn())
total += trans; // 更新总销售额
else
{
//打印前一本书的结果
std:: cout < < total < < std :: endl;
total = trans; // total 现在表示下一本书的销售额
}
}
std:: cout < < total < < std :: endl; //打印最后一本书的结果
}
else
{
//没有输入!警告读者
std:: cerr < < "No data?!" < < std :: endl;
return -1; // 表示失败
}
return 0;
}
#include "sales_item.h"
#ifndef __C__project__Sales_item__
#define __C__project__Sales_item__
#include < stdio.h >
#include < iostream >
#include < string >
class Sales_item {
// these declarations are explained section 7.2.1, p. 270
// and in chapter 14, pages 557, 558, 561
friend std::istream& operator > >(std::istream&, Sales_item&);
friend std::ostream& operator< < (std::ostream&, const Sales_item&);
friend bool operator< (const Sales_item&, const Sales_item&);
friend bool
operator==(const Sales_item&, const Sales_item&);
public:
// constructors are explained in section 7.1.4, pages 262 - 265
// default constructor needed to initialize members of built-in type
Sales_item() : units_sold(0), revenue(0.0) { }
Sales_item(const std::string &book) :
bookNo(book), units_sold(0), revenue(0.0) { }
Sales_item(std::istream &is) { is > > *this; }
public:
// operations on Sales_item objects
// member binary operator: left-hand operand bound to implicit this pointer
Sales_item& operator+=(const Sales_item&);
// operations on Sales_item objects
std::string isbn() const { return bookNo; }
double avg_price() const;
// private members as before
private:
std::string bookNo; // implicitly initialized to the empty string
unsigned units_sold;
double revenue;
};
// used in chapter 10
inline
bool compareIsbn(const Sales_item &lhs, const Sales_item &rhs)
{
return lhs.isbn() == rhs.isbn();
}
// nonmember binary operator: must declare a parameter for each operand
Sales_item operator+(const Sales_item&, const Sales_item&);
inline bool
operator==(const Sales_item &lhs, const Sales_item &rhs)
{
// must be made a friend of Sales_item
return lhs.units_sold == rhs.units_sold &&
lhs.revenue == rhs.revenue &&
lhs.isbn() == rhs.isbn();
}
inline bool
operator!=(const Sales_item &lhs, const Sales_item &rhs)
{
return !(lhs == rhs); // != defined in terms of operator==
}
// assumes that both objects refer to the same ISBN
Sales_item& Sales_item::operator+=(const Sales_item& rhs)
{
units_sold += rhs.units_sold;
revenue += rhs.revenue;
return *this;
}
// assumes that both objects refer to the same ISBN
Sales_item
operator+(const Sales_item& lhs, const Sales_item& rhs)
{
Sales_item ret(lhs); // copy (|lhs|) into a local object that we'll return
ret += rhs; // add in the contents of (|rhs|)
return ret; // return (|ret|) by value
}
std::istream&
operator > >(std::istream& in, Sales_item& s)
{
double price;
in > > s.bookNo > > s.units_sold > > price;
// check that the inputs succeeded
if (in)
s.revenue = s.units_sold * price;
else
s = Sales_item(); // input failed: reset object to default state
return in;
}
std::ostream&
operator< < (std::ostream& out, const Sales_item& s)
{
out < < s.isbn() < < " " < < s.units_sold < < " "
< < s.revenue < < " " < < s.avg_price();
return out;
}
double Sales_item::avg_price() const
{
if (units_sold)
return revenue / units_sold;
else
return 0;
}
#endif /* defined(__C__project__Sales_item__) */
五、术语表
运算符(>> operator)输入运算符。从左侧运算对象所指定的输入流读取数据,存入右侧运算对象中: cin>> i表示从标准输入读取下一个值,存入i中。输入运算符可以连接: cin>> i>> j表示先读取一个值存入i,再读取一个值存入j。
=运算符(>= operator)大于等于运算符。检测左侧运算对象是否大于等于右侧运算对象。
运算符(> operator)大于运算符。检测左侧运算对象是否大于右侧运算对象。
全部0条评论
快来发表一下你的评论吧 !