c++ - 如何在 C++11 中插入 std::map ?

标签 c++ class c++11 insert stdmap

我正在尝试将一组对值插入 中的 std::map 中。但是,这些值似乎没有插入到 std::map 中。请仔细检查我的代码。我感谢任何和所有的帮助。

#include<iostream>
#include<string>
#include<algorithm>
#include<vector>
#include<map>
#include<cstdlib>
#include<utility>
#include<ctime>

#include "print.h"

class ReportCard
{
private:
    std::map<std::string, double> m_report_card;

public:
    std::map<std::string, double> getReportCardInstance() {  return m_report_card;  }
};

class Student
{

private:
    int m_roll_no;
    std::string m_name;
    ReportCard m_reportCard;

public:
    Student(int inRollNo, const std::string& inName) :
        m_roll_no(inRollNo), m_name(inName)
    {}

    std::string getName()   {   return m_name;  } 
    int getRollNo()     {   return m_roll_no;   }
    ReportCard getReportCard()  {   return self.m_reportCard;   }
    int getReportCardSize() {   return m_reportCard.getReportCardInstance().size(); }
};

class Driver
{
private:
    std::vector<Student> student_list;
    std::vector<Student> temp;

public:
    void studentTestPopulate()
    {
        student_list.push_back(Student(1, "Tim"));
        student_list.push_back(Student(2, "Matt"));
        student_list.push_back(Student(100, "Luke"));
        student_list.push_back(Student(68, "Lissy"));
        student_list.push_back(Student(20, "Tony"));
        student_list.push_back(Student(33, "Joseph"));
        student_list.push_back(Student(14, "Sid"));
        student_list.push_back(Student(15, "Roby"));
        student_list.push_back(Student(44, "Rohan"));
        student_list.push_back(Student(11, "Kevin"));
        student_list.push_back(Student(19, "George"));
    }
    void reportCardPopulate()
    {
        for (auto& student : student_list)
        {
            std::cout << student.getName() << std::endl;
            student.getReportCard().getReportCardInstance().insert(std::make_pair<std::string, double>("Math", generateMark));
            //This is the function that does not work. No marks are printed!!
            for (auto& mark : student.getReportCard().getReportCardInstance())
            {
                std::cout << mark.first << " " << mark.second;
            }
            //student.getReportCard().getReportCardInstance().insert(std::make_pair("Science", generateMark));
            //student.getReportCard().getReportCardInstance().insert(std::make_pair("Geography", generateMark));
            //student.getReportCard().getReportCardInstance().insert(std::make_pair("French", generateMark));
            //student.getReportCard().getReportCardInstance().insert(std::make_pair("History", generateMark));
        }
    }
    void showAllStudentDetails()
    {
        for (auto& student : student_list)
        {
            std::cout << student.getName() << std::endl;
            std::cout << student.getRollNo() << std::endl;
            std::cout << "REPORT CARD : " << student.getReportCardSize() << std::endl << std::endl;
            for (auto& mark : student.getReportCard().getReportCardInstance())
            {
                std::cout << mark.first << std::endl;
                std::cout << mark.second << std::endl;
            }
        }
    }
};

int main()
{
    srand(time(NULL));
    Driver driver;
    driver.studentTestPopulate();
    driver.reportCardPopulate();
    //driver.showAllStudentDetails();
}

reportCardPopulate() 函数应该将值对插入到report_card 映射中。但是,插入功能似乎不起作用。

当我们尝试在 reportCardPopulate() 函数中打印值时,它不会打印任何内容。当我尝试打印 map 大小时,它打印0。当我使用 sizeof() 打印尺寸时,它在插入之前和之后打印相同的尺寸。

最佳答案

以下功能

std::map<std::string, double> getReportCardInstance() { ... }
//^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
ReportCard getReportCard() { ... }
//^^^^^^^^

返回 std::map<std::string, double> 的拷贝和ReportCard分别类。因此,无论您在此处插入什么内容

student.getReportCard().getReportCardInstance().insert(std::make_pair<std::string, double>("Math", generateMark));

在上述拷贝上执行,因此原始成员位于 ReportCard 中(即 m_report_card )永远不会被更新。在调用上述行之后,拷贝将被销毁,期望它起作用是没有意义的。

其次,显示的代码是错误的,因为在 C++ 中你应该使用 this不是self

ReportCard getReportCard()
{
    return self.m_reportCard;
         //^^^^ --> should be `return this->m_reportCard;`
         // or simply         `return m_reportCard;`
}

更正上述内容并通过引用返回成员将使代码正常工作。 ( See live online )

std::map<std::string, double>& getReportCardInstance()
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^
{
    return m_report_card;
}

ReportCard& getReportCard()
//^^^^^^^^
{
    return m_reportCard;
}

话虽这么说,你的ReportCardStudent如果执行上述操作,类将公开成员。这不是一个好的设计。如果这些仅用于 Driver 的内部使用类,你可以将它们保留为 private Driver的属性类。

#include <vector>
#include <map>
#include <string>
#include <iostream>


class Driver /* final */ // -> optional
{
private: // Student is private for Driver class
    class Student
    {
        // type alias is enough for the map
        using ReportCard  = std::map<std::string, double>;
    private:
        int m_roll_no;
        std::string m_name;
        ReportCard m_reportCard;

    public:
        Student(int inRollNo, const std::string& inName)
            : m_roll_no{ inRollNo }, m_name{ inName }
        {}
        // make the member functions const if they are not modifing the members
        const std::string& getName() const { return m_name; }
        int getRollNo() const { return m_roll_no; }
        ReportCard& getReportCard() { return m_reportCard; }
        std::size_t getReportCardSize() const { return m_reportCard.size(); }
    };

private:
    std::vector<Student> student_list;
    std::vector<Student> temp;

public:
    void studentTestPopulate()
    {
        // construct the `Student` in-place using `std::vector::emplace_back`
        student_list.emplace_back(1, "Tim"); 
        student_list.emplace_back(2, "Matt");
        student_list.emplace_back(100, "Luke");
        student_list.emplace_back(68, "Lissy");
        student_list.emplace_back(20, "Tony");
        student_list.emplace_back(33, "Joseph");
        student_list.emplace_back(14, "Sid");
        student_list.emplace_back(15, "Roby");
        student_list.emplace_back(44, "Rohan");
        student_list.emplace_back(11, "Kevin");
        student_list.emplace_back(19, "George");
    }

    void reportCardPopulate()
    {
        for (auto& student : student_list)
        {
            std::cout << student.getName() << "\n";

            student.getReportCard().emplace(student.getName(), 12.0);
            //                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
            // use `std::map::emplace` for constructing `ReportCard` in-place
            for (auto& mark : student.getReportCard())
            {
                std::cout << mark.first << " " << mark.second << "\n";
            }
        }
    }
    // ... other members
};

int main()
{
    Driver driver;
    driver.studentTestPopulate();
    driver.reportCardPopulate();
}

关于c++ - 如何在 C++11 中插入 std::map ?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57701329/

相关文章:

c++ - 基于一个点的角度射击子弹

c++ - gcc reverse_iterator 比较运算符丢失了吗?

c++ - 在同一个类中重载 operator< 和 operator>

Java访问类变量?

typescript - 可以省略 Typescript 类上的泛型类型

c++ - 将递归解决方案转换为迭代解决方案

c++ - __func__ 值在 C 和 C++ 之间的区别

c++ - boost :scoped_ptr<T> pimpl 的最佳选择

c++ - OpenGL - 使用片段着色器得到奇怪的结果

symfony - 如何在Symfony 4中获得有效的类(class)?