假设我有两个文本文件。文本文件“ A.txt”包含名称及其年龄。文本文件“ B.txt”包含名称及其权重。文本文件的名称顺序不同。
//text file "A.txt"
Jason 20
Jack 34
Amanda 15
Einstein 65
Kelvin 47
//text file "B.txt"
Einstein 70
Amanda 55
Jack 99
Kelvin 85
Jason 68
用最少的操作来读取和匹配这两个文本文件并将其属性设置为类的对象数组的最有效方法是什么?
class Person{
private:
string name;
int age;
int weight;
public:
//setter method
}
int main(){
Person haha[5];
//code to read files and stores into haha
}
您想使用std::unordered_map
。
您的算法总之将是这样:
std::unordered_map
实例。地图的键将是每个人唯一的一些字符串,例如姓名。并且std::unordered_map
对象是一个值。插入Person
的时间复杂度为std::unordered_map
。O(1)
中找到与Person
同名的std::unordered_map
。如果它在地图中,则为重复项,否则您将其再次插入std::unordered_map::find
。 std::unordered_map::find
的时间复杂度将为std::unordered_map
。如果要有std::unordered_map::find
个对象的数组,则可以制作一个并在其中移动对象。但是您也可以遍历O(1)
,因此可以使用它代替Person
s的数组。
如果使用现代C ++语言元素,则可以提出优雅的解决方案。
匹配事物的秘诀是使用关联容器,例如std::unordered_map
。您可以在其中存储一个键(例如名称)和一个值(例如重量),然后快速查找。
[我做出了一个设计决策:一个人只有年龄,才能负重。这意味着,如果具有权重的文件比具有年龄的文件包含的条目更多,那么我将忽略这些其他人员。
为了向您的Person类添加元素,我添加了一个构造函数,该构造函数将值简单地复制到成员变量中。重量是可选的。
而且,为了能够显示一些不错的输出,我已经覆盖了Person类的插入操作符。
两个源文本文件都包含一个Person
和一个std::map
。为了使用更简单的读取算法,我创建了一个代理类来读取std::string
。
为了读取权重文件,我们只需要定义一个映射,然后使用其范围构造函数,就可以通过integer
结合为string-int-pairs定义的Proxy类来读取所有值。请注意,最终迭代器将默认通过{}构造。并且,我们使用C ++ 17功能CTAD(“类模板参数推导”)来定义没有模板参数的std :: map。
为了匹配值,我们使用std::pair<std::string, int>
将读取年龄文件,搜索匹配的权重并将结果添加到人员向量中。
最后但并非最不重要的是,我们在显示屏上显示结果。
请参阅完整的工作示例:
std::istream_iterator