是否可以将 std::vector 传递给需要 CArray 的 MFC 函数?
Is it possible to pass a std::vector to an MFC function that expects a CArray?
我有一个
std::vector<double> vecArr
如何将它传递给函数
BOOL AddData (const CArray<double,double>& arrValue)
?
评论说这不行,建议我先把std::vector
对象转成CArray
对象。然而,这在时间上非常昂贵——我在我的机器上测量了 7 秒和 7 毫秒的差异。
// Copy vector v1 to v2 (very fast)
vector<double> v1;
v1.resize(1000000); // 1 Mio elements
vector<double> v2(v1); // ~7ms
// Copy vector v1 to CArray a1 (very slow)
CArray<double, double> a1;
a1.SetSize(v1.size()); // Reserve 1 Mio elements
vector<double>::iterator it = v1.begin();
while (it != v1.end()) // ~7sec ! :((
arr.Add(*it++);` `
有什么方法可以提高这个解决方案的性能吗?
无法将 "reinterpret" 一个 std::vector
作为一个 CArray
。虽然两者类代表的是同一个概念,但并不相同。这就像两种完全不同的语言。你可能会用俄语说同样的话,但我听不懂,因为我看不懂俄语!
你基本上有三个选择:
将 std::vector
转换为 CArray
.
就像将俄语翻译成英语一样,这需要时间。幸运的是,与语言翻译不同,这是一个微不足道的过程。您只需遍历原始 std::vector
并将每个元素复制到新的 CArray
.
如果您适当注意为所需数量的元素预先分配space,则此操作可以在O(n) 时间和space 内完成。它不是免费的,但也不是(通常)非常昂贵。
更改函数的接口,使其接受一个std::vector
对象。
可以说,这是最好的选项。您应该在标准库容器 类 上标准化并远离 MFC 容器 类。这有很多原因,包括互操作性和性能。
这样做的明显缺点是它需要对代码进行更改——可能是大量的破坏性更改——既耗时又容易出错。但这是一个非常有益的重构,无论如何都确实需要进行,除非代码完全处于生命支持状态并且没有进一步改进。重构完成后,在运行时不会有性能成本,产生一个理想的解决方案。
采用 "mixed" 解决方案 更改函数的接口以接受最小公分母参数。具体来说,更改函数使其接受 C 样式数组(一个参数是指向数组中第一个元素的指针,第二个参数表示数组的长度)。
这导致了最大的兼容性,因为 std::vector
对象和 CArray
对象都可以 treated/reinterpreted 就好像它们是基本的 C 风格数组一样,因此最大限度地减少了整个代码库所需的侵入性更改的数量。在本地,您可以使用任何方便的容器类型,然后为了互操作性,您传递最小公分母,这是很容易获得的。
此解决方案的缺点很多,并且与首先使用类型安全容器的原因相同,因此如果解决方案 #2 完全可行,您应该更愿意这样做。
我有一个
std::vector<double> vecArr
如何将它传递给函数
BOOL AddData (const CArray<double,double>& arrValue)
?
评论说这不行,建议我先把std::vector
对象转成CArray
对象。然而,这在时间上非常昂贵——我在我的机器上测量了 7 秒和 7 毫秒的差异。
// Copy vector v1 to v2 (very fast)
vector<double> v1;
v1.resize(1000000); // 1 Mio elements
vector<double> v2(v1); // ~7ms
// Copy vector v1 to CArray a1 (very slow)
CArray<double, double> a1;
a1.SetSize(v1.size()); // Reserve 1 Mio elements
vector<double>::iterator it = v1.begin();
while (it != v1.end()) // ~7sec ! :((
arr.Add(*it++);` `
有什么方法可以提高这个解决方案的性能吗?
无法将 "reinterpret" 一个 std::vector
作为一个 CArray
。虽然两者类代表的是同一个概念,但并不相同。这就像两种完全不同的语言。你可能会用俄语说同样的话,但我听不懂,因为我看不懂俄语!
你基本上有三个选择:
将
std::vector
转换为CArray
.就像将俄语翻译成英语一样,这需要时间。幸运的是,与语言翻译不同,这是一个微不足道的过程。您只需遍历原始
std::vector
并将每个元素复制到新的CArray
.如果您适当注意为所需数量的元素预先分配space,则此操作可以在O(n) 时间和space 内完成。它不是免费的,但也不是(通常)非常昂贵。
更改函数的接口,使其接受一个
std::vector
对象。可以说,这是最好的选项。您应该在标准库容器 类 上标准化并远离 MFC 容器 类。这有很多原因,包括互操作性和性能。
这样做的明显缺点是它需要对代码进行更改——可能是大量的破坏性更改——既耗时又容易出错。但这是一个非常有益的重构,无论如何都确实需要进行,除非代码完全处于生命支持状态并且没有进一步改进。重构完成后,在运行时不会有性能成本,产生一个理想的解决方案。
采用 "mixed" 解决方案 更改函数的接口以接受最小公分母参数。具体来说,更改函数使其接受 C 样式数组(一个参数是指向数组中第一个元素的指针,第二个参数表示数组的长度)。
这导致了最大的兼容性,因为
std::vector
对象和CArray
对象都可以 treated/reinterpreted 就好像它们是基本的 C 风格数组一样,因此最大限度地减少了整个代码库所需的侵入性更改的数量。在本地,您可以使用任何方便的容器类型,然后为了互操作性,您传递最小公分母,这是很容易获得的。此解决方案的缺点很多,并且与首先使用类型安全容器的原因相同,因此如果解决方案 #2 完全可行,您应该更愿意这样做。