我最近一直在将Python应用程序移植到C++,但是现在我对如何移植特定功能一无所知。以下是相应的Python代码:
def foo(a, b): # Where `a' is a list of strings, as is `b'
for x in a:
if not x in b:
return False
return True
我希望具有类似的功能:
bool
foo (char* a[], char* b[])
{
// ...
}
最简单的方法是什么?我曾尝试使用STL算法,但似乎无法使它们正常工作。例如,我目前有这个(使用glib类型):
gboolean
foo (gchar* a[], gchar* b[])
{
gboolean result;
std::sort (a, (a + (sizeof (a) / sizeof (*a))); // The second argument corresponds to the size of the array.
std::sort (b, (b + (sizeof (b) / sizeof (*b)));
result = std::includes (b, (b + (sizeof (b) / sizeof (*b))),
a, (a + (sizeof (a) / sizeof (*a))));
return result;
}
我非常愿意使用C++ 11的功能。
最佳答案
您的第一个问题与C++处理(不)处理数组的方式有关。数组存在一种非常脆弱的阴影,如果您以一种有趣的方式看待它们,它们将被转换为指针。您的函数不会像您期望的那样接受两个指向数组的指针。它需要两个指针。
换句话说,您将丢失有关数组大小的所有信息。 sizeof(a)
不能提供数组的大小。它为您提供了指针的大小。
因此,您有两个选择:快速而肮脏的临时解决方案是显式传递数组大小:
gboolean foo (gchar** a, int a_size, gchar** b, int b_size)
另外,更好的是,您可以使用 vector 代替数组:
gboolean foo (const std::vector<gchar*>& a, const std::vector<gchar*>& b)
vector 是动态大小的数组,因此,它们知道它们的大小。
a.size()
将为您提供 vector 中元素的数量。但是它们还有两个方便的成员函数begin()
和end()
,旨在与标准库算法一起使用。因此,对 vector 进行排序:
std::sort(a.begin(), a.end());
对于
std::includes
同样如此。第二个问题是您不是对字符串进行操作,而是对char指针进行操作。换句话说,
std::sort
将按指针地址而不是字符串内容进行排序。同样,您有两个选择:
如果您坚持使用char指针而不是字符串,则可以为
std::sort
指定一个自定义比较器(使用lambda,因为您在评论中提到可以使用它们)std::sort(a.begin(), a.end(), [](gchar* lhs, gchar* rhs) { return strcmp(lhs, rhs) < 0; });
同样,
std::includes
采用可选的第五个参数来比较元素。可以在其中使用相同的lambda。另外,您只需要使用
std::string
而不是char指针即可。然后默认比较器将起作用:gboolean
foo (const std::vector<std::string>& a, const std::vector<std::string>& b)
{
gboolean result;
std::sort (a.begin(), a.end());
std::sort (b.begin(), b.end());
result = std::includes (b.begin(), b.end(),
a.begin(), a.end());
return result;
}
更简单,更清洁,更安全。