ruby - How can I remove non-printable invisible characters from string?
问题描述
How can I remove non-printable invisible characters from string?
Ruby version: 2.4.1
2.4.1 :209 > product.name.gsub(/[^[:print:]]/,'.')
=> "Kanha"
2.4.1 :210 > product.name.gsub(/[^[:print:]]/,'.').length
=> 6
2.4.1 :212 > product.name.gsub(/[\u0080-\u00ff]/, '').length
=> 6
2.4.1 :214 > product.name.chars.reject { |char| char.ascii_only? and (char.ord < 32 or char.ord == 127) }.join.length
=> 6
2.4.1 :216 > product.name.gsub(/[^[:print:]]/i, '').length
=> 6
The word "Kanha" has 5 letters. However there is a 6th character that is not printable. How can I remove it?
By googling and SOing I have already tried few approaches, but as you can see none of those are helpful.
It is causing problems when I try to integrate out data with other systems.
解决方案
首先,让我们弄清楚有问题的角色是什么:
str = "Kanha"
p str.codepoints
# => [75, 97, 110, 104, 97, 8236]
前五个代码点介于 0 到 127 之间,这意味着它们是 ASCII 字符。可以安全地假设它们是字母 Kanha,尽管如果您愿意,这很容易验证:
p [75, 97, 110, 104, 97].map(&:ord)
# => ["K", "a", "n", "h", "a"]
这意味着违规字符是最后一个字符,代码点 8236。不过,这是一个十进制(以 10 为基数)数字,而 Unicode 字符通常按其十六进制(以 16 为基数)数字列出。十六进制的 8236 是 202C ( 8236.to_s(16) # => "202c"
),所以我们只需要谷歌搜索 U+202C。
谷歌很快告诉我们违规字符是U+202C POP DIRECTIONAL FORMATTING并且它是 Unicode 字符“其他,格式”类别的成员。维基百科说这个类别:
包括软连字符、连接控制字符(zwnj 和 zwj)、支持双向文本的控制字符和语言标记字符
它还告诉我们类别的“值”或代码是“Cf”。如果这些听起来像是要从字符串中删除的字符以及 U+202C,则可以在 Ruby 正则表达式中使用该\p{Cf}
属性。您也可以使用\P{Print}
(注意大写P
)作为[^[:print]]
:
str = "Kanha"
p str.length # => 6
p str.gsub(/\P{Print}|\p{Cf}/, '') # => "Kahna"
p str.gsub(/\P{Print}|\p{Cf}/, '').length # => 5
在 repl.it 上查看:https ://repl.it/@jrunning/DutifulRashTag
推荐阅读
- javascript - 在角度组件方法中通过 id 更改 div 内部 HTML 内容
- php - 如何在 PHP 中使用 simple_html_dom 导入多个 url?
- javascript - 根据选择字段中的选定项目显示信息
- reactjs - 无状态反应函数的首选语法是什么?为什么?
- php - PHP PDO 参数号无效
- python - 使用 numpy 解析 csv 会引发 TypeError
- html - 如何使用 flexbox 设置容器的最大宽度?
- javascript - 使用 Google Sheets REST API 编辑一行的单元格数据?
- bash - 在后台运行命令并稍后捕获结果(Bash)
- sql-server-2014 - 基于 SQL Server 2014 数据库生成 graphql 架构