自制披肩:外观相同但不相同

阿诺德·费尔德曼

对于我的优化,我想得到一个不错toupper的Rcpp。我是C ++的新手,据我所知:

#include <Rcpp.h>
using namespace Rcpp;

void C_toupper_String(const String& s) {
  for (char *p =(char *)s.get_cstring();*p!=0;p++) *p = toupper(*p);
}
// [[Rcpp::export]]
StringVector C_toupper(StringVector const& vecteur) {
  StringVector res=clone(vecteur);
  for (int i(0); i < res.size(); ++i) {
    C_toupper_String(res[i]);
  }
  return res;
}

/*** R
teststring <- "HeY I arNaud"
C_toupper(teststring)
toupper(teststring)
identical(C_toupper(teststring),toupper(teststring))
*/

但是,它不能正常工作。

> C_toupper(teststring)
[1] "HEY I ARNAUD"

> toupper(teststring)
[1] "HEY I ARNAUD"

> identical(C_toupper(teststring),toupper(teststring))
[1] FALSE

有什么问题?如果可能的话,我不想转换Stringstd::string,因为我想了解发生了什么:进入C ++的目的是能够避免复制和转换。

谢谢,

阿诺

康拉德·鲁道夫

为什么两个字符串不测试identical的问题很难解释-两个字符串在检查其原始字节时(通过charToRaw肯定看起来相同,它们不携带属性,并且没有编码集。因此,实际上,它们应该相同。

为了解决这个难题,我们需要了解您的C ++代码实际上在做什么。更具体地说,C风格的强制转换C_toupper_String正在做什么。因为他们危险的,你应该永远使用C-风格的转换您的代码纯粹是由于这种转换而出现问题。

为什么?因为String::get_cstring回报char const*您将其char*抛弃,从而抛弃其const本质。可能是安全的,但只有在底层存储不是const否则,它是未定义的行为(UB)由于代码重写(例如优化),UB的效果很难预测。在这种情况下,似乎会产生使R字符串内部混乱的代码。


从根本上讲,您不能Rcpp::String在适当位置修改对象,而它们不允许这样做。但是,如果您只是想避免复制,那么您的代码无论如何都无法实现其目标,因为您的C_toupper函数会在第一步中明确复制输入。

正如Dirk所说,解决此问题的正确方法是使用可用的Rcpp API。对于字符串修改,这意味着将您的输入转换为std::string,执行修改,然后再转换回。这确实会复制,但是您当前的代码也会复制。这是编写此代码的一种好方法:

#include <Rcpp.h>
#include <cctype>
#include <string>

// [[Rcpp::export]]
Rcpp::StringVector C_toupper(Rcpp::StringVector const& vec) {
    std::vector<std::string> res(vec.begin(), vec.end());
    for (std::string& str : res) {
        for (char& c : str) c = std::toupper(c);
    }

    return Rcpp::wrap(res);
}

注意,这有时会产生错误的结果,因为std::toupper从根本不能与某些Unicode的特性处理。R的toupper效果更好,但也有一些问题。合适溶液是使用{stringr}或{stringi}包。

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

外观相同的 Python 数据框不相同

来自分类Dev

PHP相同的字符串但不相同

来自分类Dev

Doskey中的`^&`和$$`行为相似但不相同

来自分类Dev

父母相似但不相同时如何抓

来自分类Dev

MySQL查找相似但不相同的记录

来自分类Dev

各节的级别不相同

来自分类Dev

为什么sapply()和tapply()具有相同的结果,但不相同?

来自分类Dev

生成15个可能相同2次但不相同3次的随机数

来自分类Dev

在场景上渲染许多相似但不相同的网格

来自分类Dev

将列中相似(但不相同)的数据合并到单行中

来自分类Dev

Openrefine:cross.cell用于相似但不相同的值

来自分类Dev

总结具有相似但不相同的x值的变量

来自分类Dev

创建以匹配(但不相同)结尾的文件夹列表

来自分类Dev

Openrefine:cross.cell用于相似但不相同的值

来自分类Dev

维护 2 个具有相似代码但不相同的分支

来自分类Dev

Swift通用数组“不相同”错误

来自分类Dev

表单输入字段的间距不相同

来自分类Dev

表单输入字段的间距不相同

来自分类Dev

Swift通用数组“不相同”错误

来自分类Dev

替换后跟不相同字符的字符

来自分类Dev

在Makefile中以相同或不相同的标记结束`define`的区别?

来自分类Dev

几乎相同的代码,但答案却大不相同

来自分类Dev

具有相同参数但大小不相同的JTextArea

来自分类Dev

Python相同的数据不相同,并且功能不同

来自分类Dev

几乎相同的代码,但答案却大不相同

来自分类Dev

Python / Pandas-根据数据框中以下条件删除行(类似于删除重复项,但不相同)

来自分类Dev

对于两个相似但不相同的数据列,需要一个VLOOKUP公式

来自分类Dev

熊猫仅使用小写字母将数据帧连接在相似但不相同的字符串上

来自分类Dev

从两个数据帧创建数据帧,两个数据帧的周期索引重叠但不相同

Related 相关文章

  1. 1

    外观相同的 Python 数据框不相同

  2. 2

    PHP相同的字符串但不相同

  3. 3

    Doskey中的`^&`和$$`行为相似但不相同

  4. 4

    父母相似但不相同时如何抓

  5. 5

    MySQL查找相似但不相同的记录

  6. 6

    各节的级别不相同

  7. 7

    为什么sapply()和tapply()具有相同的结果,但不相同?

  8. 8

    生成15个可能相同2次但不相同3次的随机数

  9. 9

    在场景上渲染许多相似但不相同的网格

  10. 10

    将列中相似(但不相同)的数据合并到单行中

  11. 11

    Openrefine:cross.cell用于相似但不相同的值

  12. 12

    总结具有相似但不相同的x值的变量

  13. 13

    创建以匹配(但不相同)结尾的文件夹列表

  14. 14

    Openrefine:cross.cell用于相似但不相同的值

  15. 15

    维护 2 个具有相似代码但不相同的分支

  16. 16

    Swift通用数组“不相同”错误

  17. 17

    表单输入字段的间距不相同

  18. 18

    表单输入字段的间距不相同

  19. 19

    Swift通用数组“不相同”错误

  20. 20

    替换后跟不相同字符的字符

  21. 21

    在Makefile中以相同或不相同的标记结束`define`的区别?

  22. 22

    几乎相同的代码,但答案却大不相同

  23. 23

    具有相同参数但大小不相同的JTextArea

  24. 24

    Python相同的数据不相同,并且功能不同

  25. 25

    几乎相同的代码,但答案却大不相同

  26. 26

    Python / Pandas-根据数据框中以下条件删除行(类似于删除重复项,但不相同)

  27. 27

    对于两个相似但不相同的数据列,需要一个VLOOKUP公式

  28. 28

    熊猫仅使用小写字母将数据帧连接在相似但不相同的字符串上

  29. 29

    从两个数据帧创建数据帧,两个数据帧的周期索引重叠但不相同

热门标签

归档