64,692
社区成员
发帖
与我相关
我的任务
分享
#include <algorithm>
#include <fstream>
#include <list>
#include <set>
#include <string>
namespace {
std::string kF1 = "1.txt";
std::string kF2 = "2.txt";
const char kDelimiter = ' ';
} // namespace
// Before loading data to container, there is a chance to modify a line by using
// paramter function_process_line who is a function pointer.
// Set it NULL, if you need not preprocess an input line.
template<typename ContainerType>
ContainerType LoadDataToContainer(const std::string& filename,
void(*function_process_line)(std::string&)) {
std::ifstream infile(filename, std::ios_base::in);
if (!infile) {
throw std::ios_base::failure("Failed to open file: " + filename);
}
ContainerType container;
std::string line;
while (infile) {
std::getline(infile, line);
if (line.empty()) {
break;
}
if (function_process_line) {
function_process_line(line);
}
// Note: parameter 1 is not meaningful to any container type.
container.insert(container.end(), line);
}
infile.close();
return container;
}
template<typename IteratorType>
void WriteDataToFile(
const std::string& filename, const IteratorType& b, const IteratorType& e) {
std::ofstream outfile(filename, std::ios_base::out);
if (!outfile) {
throw std::ios_base::failure("Failed to open file: " + filename);
}
for (IteratorType iter = b; iter != e; ++iter) {
outfile << *iter << std::endl;
}
outfile.close();
}
inline void RetainOnlyFirstColumn(std::string& line) {
// To keep things simple, it is assumed there must be kDelimiter in line.
line.erase(line.begin() + line.find(kDelimiter), line.begin() + line.size());
}
int main(int argc, char* argv[]) {
auto s = LoadDataToContainer<std::set<std::string>>(kF1, RetainOnlyFirstColumn);
auto l = LoadDataToContainer<std::list<std::string>>(kF2, NULL);
for (auto iter = l.begin(); iter != l.end();
iter = (s.find(iter->substr(0 ,iter->find(kDelimiter))) != s.end()) ?
l.erase(iter) : ++iter
);
WriteDataToFile(kF2, l.begin(), l.end());
}