我有一个从文件中读取行的函数,并将每行中的每个字符串存储在向量中。
void openf(std::string s)
{
std::string line;
std::string b;
std::ifstream in;
in.open(s);
std::vector<std::string> vec;
if(in.is_open()) {
std::cout << "File is open\n" << std::endl;
while(std::getline(in,line)) {
for(decltype(line.size()) i = 0; i != line.size(); ++i) {
if(isspace(line[i]) || ispunct(line[i])) {
vec.push_back(b);
b = "";
}
else {
b += line[i];
}
}
}
}
for(auto a:vec)
std::cout << a << std::endl;
in.close();
}
这个工作。
但如果我这样做
if(!isspace(line[i]) || !ispunct(line[i])) {
b += line[i];
}
else {
vec.push_back(b);
b = "";
}
什么都没打印。
如果我没有逻辑OR语句,只需单独使用!isspace和!ispunct,程序的行为就像它在相应情况下所期望的那样。
我认为我不需要,但我也尝试在每个操作员周围放置(),这样就不会互相干扰。仍然行不通。
看起来像是相同的代码。为什么它不会在一个案例中起作用而在另一个案例中起作用呢?
答案 0 :(得分:13)
你有:
if (A || B)
do this
else
do that
要否定这一点,你需要:
if (!(A || B))
do that
else
do this
并!(A || B)
向(!A && !B)
所以你需要写
if (!isspace(line[i]) && !ispunct(line[i]))
有关详细信息,请参阅DeMorgan's Laws。
答案 1 :(得分:5)
参考 - De-Morgan's Law
将||
更改为&&
(!A && !B) = !(A || B)
所以使用,
(!isspace(line[i]) && !ispunct(line[i]))
^^
以你的第二种方式
答案 2 :(得分:3)
这不是您在工作代码中检查的条件的反转。这是:
if(!isspace(line[i]) && !ispunct(line[i])) {
b += line[i];
}
else {
vec.push_back(b);
b = "";
}
! isspace(x) || ! ispunct(x)
始终为true
。一个空间不会是标点符号;惩罚不会成为太空。
答案 3 :(得分:1)
应该是:
if( !(isspace(line[i]) or ispunct(line[i])) )
b += line[i];
else {
vec.push_back(b);
b = "";
}
请参阅this post