栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > C/C++/C#

《C++ Primer》第8章 8.2节习题答案

C/C++/C# 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

《C++ Primer》第8章 8.2节习题答案

《C++ Primer》第8章 IO库

8.2  文件输入输出习题答案

练习8.4:编写函数,以读模式打开一个 文件,将其内容读入到一个string的vector中,将每一行作为一个独立的元素存于vector中。

【出题思路】

本题练习文件输入和流的逐行输入,还练习了使用迭代器遍历容器中的元素。

【解答】

data.txt里的内容

C++ is a middle-level programming language developed
by Bjarne Stroustrup starting in 1979 at Bell Labs.
C++ runs on a variety of platforms, such as Windows,
Mac OS, and the various versions of UNIX.

#include 
#include 
#include 
#include 

using namespace std;

int main()
{
    ifstream in("../chapter08/data.txt");   //打开文件
    cout << "输入字符串; " << endl;
    if(!in)
    {
        cerr << "无法打开输入文件" << endl;
        return -1;
    }

    string line;
    vector words;
    while(getline(in, line))//从文件中读取一行
    {
        words.push_back(line);//添加到vector中
    }

    in.close();     //输入完毕,关闭文件

    vector::const_iterator it = words.begin();  //迭代器
    while(it != words.end())//遍历vector
    {
        cout << *it << endl;//输出vector中的元素
        ++it;
    }

    return 0;
}

运行结果:

 练习8.5:重写上面的程序,将每个单词作为一个独立的元素进行存储。

【出题思路】

本题练习逐个数据的输入方式。

【解答】

将第18行的while (getline(in, line)){

改为while (in >> line){即可。

#include 
#include 
#include 
#include 

using namespace std;

int main()
{
    ifstream in("../chapter08/data.txt");   //打开文件
    cout << "输入字符串; " << endl;
    if(!in)
    {
        cerr << "无法打开输入文件" << endl;
        return -1;
    }

    string line;
    vector words;
    while(in >> line)           //从文件中读取每一个单词
    {
        words.push_back(line);//添加到vector中
    }

    in.close();     //输入完毕,关闭文件

    vector::const_iterator it = words.begin();  //迭代器
    while(it != words.end())//遍历vector
    {
        cout << *it << endl;//输出vector中的元素
        ++it;
    }

    return 0;
}

 运行结果:

练习8.6:重写7.1.1节的书店程序(第229)页,从一个文件中读取交易记录。将文件名作为一个参数传递给main(参见6.2.5节,第196页)。

【出题思路】

通过一个较大的例子继续练习文件输入,并练习从命令行获取参数及参数合法性的检测。

【解答】

#ifndef PROGRAM08_06_H
#define PROGRAM08_06_H

#include 
#include 


class Sales_data {

    friend std::istream& operator >> (std::istream&, Sales_data&);
    friend std::ostream& operator << (std::ostream&, const Sales_data&);
    friend bool operator < (const Sales_data&, const Sales_data&);
    friend bool operator == (const Sales_data&, const Sales_data&);

    friend Sales_data add(const Sales_data &lhs, const Sales_data &rhs);
    friend std::istream &read(std::istream &is, Sales_data &item);
    friend std::ostream &print(std::ostream &os, const Sales_data &item);

public:

    Sales_data() = default;

    Sales_data(const std::string &book): bookNo(book)
    {
        //std::cout << "call ======Sales_data(const std::string &book): bookNo(book)=============" << std::endl;
    }
    //explicit Sales_data(std::istream &is)
    Sales_data(std::istream &is)
    {
        //std::cout << "call ======Sales_data(std::istream &is)=============" << std::endl;
        is >> *this;
    }

    Sales_data(const std::string &book, const unsigned num, const double sellp, const double salep);



//定义公有函数成员
public:
    Sales_data& operator += (const Sales_data&);

    double avg_price() const;
    std::string isbn() const { return bookNo; }
    //combine函数用于把两个ISBN相同的销售记录合并在一起
    Sales_data& combine(const Sales_data &rhs)
    {
        units_sold += rhs.units_sold;                   //累加书籍的销售量
        saleprice = (rhs.saleprice * rhs.units_sold + saleprice * units_sold)
                    / (rhs.units_sold + units_sold);    //重新计算实现销售价格
        discount = saleprice / sellingprice;            //重新计算实际折扣
        revenue += rhs.revenue;                         //总销售额
        return *this;                                   //返回合并后的结果
    }



// 定义私有数据成员
private:
    std::string bookNo;             // 书籍编号,隐式初始化为空串
    unsigned units_sold = 0;        // 销售量,显式初始化为0
    double sellingprice = 0.0;      // 原始价格,显式初始化为0.0
    double saleprice = 0.0;         // 实售价格,显式初始化为0.0
    double discount = 0.0;          // 折扣,显式初始化为0.0
    double revenue = 0.0;           // 总收入
};


Sales_data::Sales_data(const std::string &book, const unsigned num, const double sellp, const double salep)
{
    bookNo = book;
    units_sold = num;
    sellingprice = sellp;
    saleprice = salep;
    if(0 != sellingprice)
    {
        discount = saleprice / sellingprice;   //计算实际折扣
    }
}

//add
Sales_data add(const Sales_data &lhs, const Sales_data &rhs)
{
    Sales_data sum = lhs;
    sum.combine(rhs);
    return sum;
}

//read
std::istream& read(std::istream &is, Sales_data &item)
{
    is >> item.bookNo >> item.units_sold >> item.sellingprice >> item.saleprice;

    return is;
}

//print
std::ostream& print(std::ostream &os, const Sales_data &item)
{
    os << item.isbn() << " " << item.units_sold << "  " << item.sellingprice << "  " << item.saleprice
    << "  " << item.discount;
    return os;
}

inline bool compareIsbn(const Sales_data &lhs, const Sales_data &rhs)
{
    return lhs.isbn() == rhs.isbn();
}

Sales_data operator + (const Sales_data&, const Sales_data&);


inline bool operator == (const Sales_data &lhs, const Sales_data &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_data &lhs, const Sales_data &rhs)
{
    return !(lhs == rhs); // != defined in terms of operator==
}

Sales_data& Sales_data::operator += (const Sales_data& rhs)
{
    units_sold += rhs.units_sold;
    revenue += rhs.revenue;
    return *this;
}


// assumes that both objects refer to the same ISBN
Sales_data operator + (const Sales_data& lhs, const Sales_data& rhs)
{
    Sales_data 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
}


//接收4个参数分别为:ISBN,销售量,原价,实际售价
std::istream& operator >> (std::istream& in, Sales_data& s)
{
    in >> s.bookNo >> s.units_sold >> s.sellingprice >> s.saleprice;
    // check that the inputs succeeded
    if (in)
        s.revenue = s.units_sold * s.saleprice;
    else
        s = Sales_data();  // input failed: reset object to default state
    return in;
}

std::ostream& operator << (std::ostream& out, const Sales_data& s)
{
    out << s.isbn() << " " << s.units_sold << " "
        << s.revenue << " " << s.avg_price();
    return out;
}

double Sales_data::avg_price() const
{
    if (units_sold)
        return revenue / units_sold;
    else
        return 0;
}

#endif // PROGRAM08_06_H

 

#include 
#include 
#include 
#include 
#include "program08_06.h"

using namespace std;

int main(int argc, char *argv[])
{
    if(argc != 2)
    {
        cerr << "请给出文件名" << endl;
        return -1;
    }
    cout << "文件名:" << argv[1] << endl;
    ifstream in(argv[1]);
    if(!in)
    {
        cerr << "无法打开输入的文件" << endl;
        return -1;
    }

    Sales_data total;                                           //保存当前求和结果的变量
    if(read(in, total))                                         //读入第一笔交易
    {
        Sales_data trans;                                       //保存下一条交易数据的变量
        while(read(in, trans))                                  //读入剩余的交易
        {
            if(total.isbn() == trans.isbn())                    //检查isbn
            {
                total.combine(trans);                           //更新变量total当前的值
            }
            else
            {
                print(cout, total) << endl;                     //输出结果
                total = trans;                                  //处理下一本书
            }
        }
        print(cout, total) << endl;                             //输出最后一条交易
    }
    else                                                        //没有输入任何信息
    {
        cerr << "没有数据" << endl;                              //通知用户
    }

    return 0;
}

QtCeate调试参数设置

 运行结果:

 

练习8.7:修改上一节的书店程序,将结果保存到一个文件中。将输出文件名作为第二个参数传递给main函数。

【出题思路】

本题练习文件输出。

【解答】

头文件与练习8.6 一样。

#include 
#include 
#include 
#include 
#include "program08_06.h"

using namespace std;

int main(int argc, char *argv[])
{
    if(argc != 3)
    {
        cerr << "请给出输入,输出文件名" << endl;
        return -1;
    }
    cout << "输入文件名:" << argv[1] << endl;
    cout << "输出文件名:" << argv[2] << endl;
    ifstream in(argv[1]);
    if(!in)
    {
        cerr << "无法打开输入的文件" << endl;
        return -1;
    }

    ofstream out(argv[2]);
    if(!out)
    {
        cerr << "无法打开输出文件" << endl;
        return -1;
    }

    Sales_data total;                                           //保存当前求和结果的变量
    if(read(in, total))                                         //读入第一笔交易
    {
        Sales_data trans;                                       //保存下一条交易数据的变量
        while(read(in, trans))                                  //读入剩余的交易
        {
            if(total.isbn() == trans.isbn())                    //检查isbn
            {
                total.combine(trans);                           //更新变量total当前的值
            }
            else
            {
                print(out, total) << endl;                     //输出结果
                total = trans;                                  //处理下一本书
            }
        }
        print(out, total) << endl;                             //输出最后一条交易
    }
    else                                                        //没有输入任何信息
    {
        cerr << "没有数据" << endl;                              //通知用户
    }

    return 0;
}

设置输出参数

  运行结果:

 

 

练习8.8:修改上一题的程序,将结果追加到给定的文件末尾。对同一个输出文件,运行程序至少两次,检验数据是否得以保留。

【出题思路】

本题练习文件的追加模式。

【解答】

将上一题程序的第19行ofstream out l(argv[2]);

改为ofstream out(argv[2],ofstream::app);。

 头文件也练习8.6 一样

#include 
#include 
#include 
#include 
#include "program08_06.h"

using namespace std;

int main(int argc, char *argv[])
{
    if(argc != 3)
    {
        cerr << "请给出输入,输出文件名" << endl;
        return -1;
    }

    ifstream in(argv[1]);
    if(!in)
    {
        cerr << "无法打开输入的文件" << endl;
        return -1;
    }

    ofstream out(argv[2], ofstream::app);                       //文件追加
    if(!out)
    {
        cerr << "无法打开输出文件" << endl;
        return -1;
    }

    Sales_data total;                                           //保存当前求和结果的变量
    if(read(in, total))                                         //读入第一笔交易
    {
        Sales_data trans;                                       //保存下一条交易数据的变量
        while(read(in, trans))                                  //读入剩余的交易
        {
            if(total.isbn() == trans.isbn())                    //检查isbn
            {
                total.combine(trans);                           //更新变量total当前的值
            }
            else
            {
                print(out, total) << endl;                     //输出结果
                total = trans;                                  //处理下一本书
            }
        }
        print(out, total) << endl;                             //输出最后一条交易
    }
    else                                                        //没有输入任何信息
    {
        cerr << "没有数据" << endl;                              //通知用户
    }

    cout << "run sucess============" << endl;
    return 0;
}

设置命令行参数

 第一次运行:

 第二次运行:

 

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/296247.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号