gpt4 book ai didi

c++ - std::sort 与本地类型比较

转载 作者:太空狗 更新时间:2023-10-29 20:41:29 25 4
gpt4 key购买 nike

下面的例子

// file mysort.cc
#include <string>
#include <vector>
#include <algorithm>
#include <string.h>

void mysort (const char**tab, unsigned size) {
std::vector<int> vecix;
vecix.resize(size);
struct CompareIndex {
const char**t;
CompareIndex(const char**p) : t(p) {};
bool operator() (int l, int r) {
return strcmp(t[l], t[r])<0;
}
};
CompareIndex compix(tab);
for (unsigned ix=0; ix<size; ix++) vecix[ix] = ix;
std::stable_sort(vecix.begin(), vecix.end(), compix);
std::vector<const char*> vecstr;
vecstr.resize(size);
for (unsigned ix=0; ix<size; ix++) vecstr[ix] = tab[vecix[ix]];
for (unsigned ix=0; ix<size; ix++) tab[ix] = vecstr[ix];
}

编译失败(在 C++03 标准的 Debian/Sid/x86-64 上使用 GCC 4.8.2)

mysort.cc: In function 'void mysort(const char**, unsigned int)':
mysort.cc:19:58: error: no matching function for call to
'stable_sort(std::vector<int>::iterator,
std::vector<int>::iterator,
mysort(const char**, unsigned int)::CompareIndex&)'
std::stable_sort(vecix.begin(), vecix.end(), compix);
^


In file included from /usr/include/c++/4.8/algorithm:62:0,
from mysort.cc:4:
/usr/include/c++/4.8/bits/stl_algo.h:5682:5: note:
template<class _RAIter, class _Compare>
void std::stable_sort(_RAIter, _RAIter, _Compare)
stable_sort(_RandomAccessIterator __first, _RandomAccessIterator __last,
^
/usr/include/c++/4.8/bits/stl_algo.h:5682:5: note:
template argument deduction/substitution failed:
mysort.cc: In substitution of 'template<class _RAIter, class _Compare>
void std::stable_sort(_RAIter, _RAIter, _Compare)
[with _RAIter = __gnu_cxx::__normal_iterator<int*, std::vector<int> >;
_Compare = mysort(const char**, unsigned int)::CompareIndex]':
mysort.cc:19:58: required from here
mysort.cc:19:58: error: template argument for
'template<class _RAIter, class _Compare>
void std::stable_sort(_RAIter, _RAIter, _Compare)'
uses local type 'mysort(const char**, unsigned int)::CompareIndex'
std::stable_sort(vecix.begin(), vecix.end(), compix);
^
mysort.cc:19:58: error: trying to instantiate
'template<class _RAIter, class _Compare>
void std::stable_sort(_RAIter, _RAIter, _Compare)'

上面是用GCC 4.8编译的使用

  g++ -Wall -c mysort.cc

我遇到了同样的错误

  g++ -std=c++03 -Wall -c mysort.cc

或与

  g++ -std=c++98 -Wall -c mysort.cc

但没有错误

  g++ -std=c++11 -c mysort.cc

鉴于我的 g++ -vgcc 版本 4.8.2 (Debian 4.8.2-12)

但使用 Clang/LLVM 3.4编译

  clang++ -Wall -c mysort.cc

我只收到警告:

  mysort.cc:19:7: warning: template argument uses local 
type 'CompareIndex'
[-Wlocal-type-template-args]
std::stable_sort(vecix.begin(), vecix.end(), compix);
^~~
1 warning generated.

(当将 -std=c++03-std=c++98 传递给 clang++ 时,我仍然只收到警告而不是错误 但没有警告 clang++ -std=c++11)

所以我的问题是:为什么 GCC 的错误和 Clang 的警告?我的代码是否合法且没有未定义的行为(w.r.t. C++03 标准)?我应该在我的编译单元中将我的 CompareIndex 设为全局 struct 吗?

动机

当然,这是一种对 C 字符串数组进行排序的愚蠢方法。真正的代码有点不同。事实上,我正在尝试在我的 MELT 中使用 std::stable_sort插件(一种用于扩展和自定义 GCC 的领域特定语言)。 MELT 正在生成 C++ 代码并有一个复制 garbage collector (因此指针由 GC 移动)。因此,我需要使用索引数组进行排序:比较函数实际上调用了一个 MELT 闭包(它可以在任意时刻触发复制 GC),因此我需要按索引(而不是原始指针)进行排序。我想让 MELT 生成的 C++ 代码符合编译 GCC 所需的 C++ 标准(03 或 98)。

解决方法

感谢juanchopanza's answer我通过在 mysort 之前在全局范围内移动 CompareIndex 的声明解决了这个问题。

我刚刚提交了 GCC 的 MELT 分支的 svn 修订版 206748;它的文件 gcc/melt/warmelt-base.melt 现在包含一个 multiple_sort_new MELT 函数(当它运行良好时替换 multiple_sort)使用 std::stable_sort,以及生成的 C++ 代码中的全局 Melt_Sort_Compare_Index 类。

最佳答案

在 C++03 中不允许使用局部类型作为模板参数。

来自 ISO/IEC 14882,14.3.1 模板类型参数 [temp.arg.type]:

A local type, a type with no linkage, an unnamed type or a type compounded from any of these types shall not be used as a template-argument for a template type-parameter.

给出的例子是这样的:

template <typename T> struct Foo {};

void foo()
{
struct Bar {};
Foo<Bar> b1; // error: local type used as template-argument
Foo<Bar*> x4; // error: pointer to local type used as template-argument
}

此限制已在 C++11 中取消。

关于c++ - std::sort 与本地类型比较,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21201685/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com