C++ 简单的向量交换只能部分工作
我有一对向量C++ 简单的向量交换只能部分工作,c++,sorting,C++,Sorting,我有一对向量pairedv,包含数据度量名称和索引。至少测试数据的大小约为780次测量,大约一半是水,一半是其他液体。因为我希望这个程序的文件输出尽可能友好,所以我尝试将输出预分类为两个部分,一个是“水”部分,另一个是“其他”部分 在下面代码的最后一个循环中,我有一个bool向量mask,当它对应的测量名称不包含“water”或任何常见变量时使用。如果bool[i]返回true,它将增加一个计数器以供以后使用,否则它将查找下一个“水”测量值,并切换两个元素的值 #包括 #包括 #包括 #包括
pairedv
,包含数据度量名称和索引。至少测试数据的大小约为780次测量,大约一半是水,一半是其他液体。因为我希望这个程序的文件输出尽可能友好,所以我尝试将输出预分类为两个部分,一个是“水”部分,另一个是“其他”部分
在下面代码的最后一个循环中,我有一个bool向量
mask,当它对应的测量名称不包含“water”或任何常见变量时使用。如果bool[i]
返回true,它将增加一个计数器以供以后使用,否则它将查找下一个“水”测量值,并切换两个元素的值
#包括
#包括
#包括
#包括
#包括
使用名称空间std;
bool IsWater(常量字符串和str1){
if(str1.find(“water”)!=string::npos)
返回(真);
//测试文件水测量仅包含“*水*”,其余部分用于冗余
if(str1.find(“Water”)!=string::npos)
返回(真);
if(str1.find(“WATER”)!=string::npos)
返回(真);
if(str1.find(“H2O”)!=string::npos)
返回(真);
if(str1.find(“h2o”)!=string::npos)
返回(真);
返回false;
}
int main(int argc,char*argv[]){
//pairedv用值初始化
//对应于度量名称、索引
向量boolv;
对于(inti=0;i您可以使用std::partition
(或std::stable\u partition
):
std::vector pairedv/*=…*/;
自动isPairWater=[](const auto&p){return IsWater(p.first);};
auto it=std::partition(pairedv.begin()、pairedv.end()、isPairWater);
//水会被排出,开始;它会被排出[
//不会是水[
使用标准的库排序。你只需要实现一个比较函数。@Anomail的尝试对我不起作用。它给了我一个更加混乱的输出。@poison\u我们不会重新发明轮子。你可以发布你的代码和特定错误。@Anomail我的代码被发布了。它不会输出错误,所以我怎么能发布错误呢?这很简单ply并没有以统一的方式组织输入。我甚至说有一种解决方法,但这需要做两次相同的事情,这远远不是最优的。您键入的代码返回错误:error:binding'const std::u cxx11::basic_string'到类型为'std:u cxx11::string&{aka std:u cxx11::basic_string&}'丢弃限定符|
删除常量
确实解决了这一问题,它确实有效,被接受。但我为什么要省略常量
?这是因为Lambda表达式吗?(自学,至今Lambda对我来说还是陌生的)编辑:忽略const
上的注释,我现在看到您对我的代码的编辑。是否需要const
一个无论如何都不会被函数更改的变量?添加const
可以更好地解释这一点,并且编译器强制执行此检查。
#include <algorithm>
#include <iostream>
#include <iterator>
#include <string>
#include <vector>
using namespace std;
bool IsWater(const string &str1){
if(str1.find("water")!=string::npos)
return (true);
//test file water measurements contain "*water*" only, remainder are for redundancy
if(str1.find("Water")!=string::npos)
return (true);
if(str1.find("WATER")!=string::npos)
return (true);
if(str1.find("H2O")!=string::npos)
return (true);
if(str1.find("h2o")!=string::npos)
return (true);
return false;
}
int main(int argc, char* argv[]){
//pairedv is initialized with <string,int> values
//corresponding to measurement name, index
vector<bool> boolv;
for(int i=0;i<pairedv.size();i++){
//fill bool vector with true if name contains water or variant
if(IsWater(pairedv[i].first))
boolv.push_back(true);
else
boolv.push_back(false);
}
//initialize 'x' as counter; will be used later to split std::sort into halves
int x=0;
for(int i=0;i<boolv.size();i++){
if(boolv[i])
x++; //if water, only increment x
else{ //if NOT water, swap with next "water" found
for(int i2=i+1;i2<boolv.size();i2++){
if(boolv[i2]){
string tempstr=pairedv[i].first;
int tempint=pairedv[i].second;
pairedv[i]=pairedv[i2];
pairedv[i2]=make_pair(tempstr,tempint);
}
}
}
}
//...
return 0;
}
std::vector<std::pair<std::string, int>> pairedv /* = ...*/;
auto isPairWater = [](const auto& p) { return IsWater(p.first); };
auto it = std::partition(pairedv.begin(), pairedv.end(), isPairWater);
// water would be [pairedv.begin(); it[
// not water would be [it, pairedv.end()[