如何在 C++ 中检查字符串的特定条件
how to check a string for specific conditions in C++
以下代码片段显示了我当前输出的一小部分:
1464: ebfffe4d bl da0 <memcpy@plt>
14bc: ebfffe37 bl da0 <memcpy@plt>
输出中的每一行都引用一个字符串。我想要实现的是,在这个
只有 memcpy@plt 才会打印一次。当字符串包含“bl”时,则名称
<...> 内应该打印并且只打印一次,因为 <...> 内的名称是相同的
在这两种情况下。有没有办法得到这个?
我当前的代码如下所示:
class CallFunction {
private:
vector<string> content;
public:
CallFunction(vector<string> content) {
this->content = content;
}
void print() {
for(string line: content) {
if(line.find("bl") != std::string::npos
&& line.find("<") != std::string::npos) {
cout << line << endl;
}
}
}
};
int main() {
string fileName = "libndkmod.s";
vector<string> content = readFile(fileName);
CallFunction cf = CallFunction(content);
cf.print();
}
在此先致谢并致以亲切的问候!
我们可以使用unordered_set
去重子串,如果相同的子串已经被打印过,则跳过它。
这一步可以抽成一个方法跟在single responsibility principle之后,比在print
函数中处理重复更自然,这个工作就交给你了。
我们使用 unordered_set
而不是 std::set
因为 unordered_set
会更快搜索。
我已经将 for 循环从 for(string line: content)
更改为 for(const string& line: content)
,然后我们避免了原始字符串的副本,以提高性能。基本上,我们更愿意对除原始类型之外的对象使用 for(const auto& item:...)
以避免复制。
我们存储了c++17引入的string_view
来避免复制子字符串,它会节省内存,因为我们避免了不必要的复制。
#include <iostream>
#include <string>
#include <unordered_set>
#include <vector>
using namespace std;
class CallFunction {
private:
vector<string> content;
public:
CallFunction(vector<string> content) { this->content = content; }
void print() {
std::unordered_set<std::string_view> mem;
for (const string& line : content) {
auto left_pos = line.find("bl");
auto right_pos = line.find(">");
if (left_pos != std::string::npos && right_pos != std::string::npos) {
std::string_view sub_view = {&line.front() + left_pos,
right_pos - left_pos + 1};
if (mem.count(sub_view)) continue;
mem.insert(sub_view);
cout << line << endl;
}
}
}
};
int main() {
string fileName = "libndkmod.s";
vector<string> content = {
"1464: ebfffe4d bl da0 <memcpy@plt>",
"14bc: ebfffe37 bl da0 <memcpy@plt>",
"14bc: ebfffe37 bl da0 <memcmp@plt>"};
CallFunction cf = CallFunction(content);
cf.print();
}
以下代码片段显示了我当前输出的一小部分:
1464: ebfffe4d bl da0 <memcpy@plt>
14bc: ebfffe37 bl da0 <memcpy@plt>
输出中的每一行都引用一个字符串。我想要实现的是,在这个 只有 memcpy@plt 才会打印一次。当字符串包含“bl”时,则名称 <...> 内应该打印并且只打印一次,因为 <...> 内的名称是相同的 在这两种情况下。有没有办法得到这个? 我当前的代码如下所示:
class CallFunction {
private:
vector<string> content;
public:
CallFunction(vector<string> content) {
this->content = content;
}
void print() {
for(string line: content) {
if(line.find("bl") != std::string::npos
&& line.find("<") != std::string::npos) {
cout << line << endl;
}
}
}
};
int main() {
string fileName = "libndkmod.s";
vector<string> content = readFile(fileName);
CallFunction cf = CallFunction(content);
cf.print();
}
在此先致谢并致以亲切的问候!
我们可以使用unordered_set
去重子串,如果相同的子串已经被打印过,则跳过它。
这一步可以抽成一个方法跟在single responsibility principle之后,比在print
函数中处理重复更自然,这个工作就交给你了。
我们使用 unordered_set
而不是 std::set
因为 unordered_set
会更快搜索。
我已经将 for 循环从 for(string line: content)
更改为 for(const string& line: content)
,然后我们避免了原始字符串的副本,以提高性能。基本上,我们更愿意对除原始类型之外的对象使用 for(const auto& item:...)
以避免复制。
我们存储了c++17引入的string_view
来避免复制子字符串,它会节省内存,因为我们避免了不必要的复制。
#include <iostream>
#include <string>
#include <unordered_set>
#include <vector>
using namespace std;
class CallFunction {
private:
vector<string> content;
public:
CallFunction(vector<string> content) { this->content = content; }
void print() {
std::unordered_set<std::string_view> mem;
for (const string& line : content) {
auto left_pos = line.find("bl");
auto right_pos = line.find(">");
if (left_pos != std::string::npos && right_pos != std::string::npos) {
std::string_view sub_view = {&line.front() + left_pos,
right_pos - left_pos + 1};
if (mem.count(sub_view)) continue;
mem.insert(sub_view);
cout << line << endl;
}
}
}
};
int main() {
string fileName = "libndkmod.s";
vector<string> content = {
"1464: ebfffe4d bl da0 <memcpy@plt>",
"14bc: ebfffe37 bl da0 <memcpy@plt>",
"14bc: ebfffe37 bl da0 <memcmp@plt>"};
CallFunction cf = CallFunction(content);
cf.print();
}