【问题标题】:How to replace a range of binary characters如何替换一系列二进制字符
【发布时间】:2017-05-25 10:22:30
【问题描述】:

如何替换一系列二进制字符,类似于在正则表达式中有一系列常规字符 ("[a-z]")?我正在尝试这个:

2.4.0 :016 > text.gsub([160.chr-194.chr], ' ')
NoMethodError: undefined method `-' for "\xA0":String
Did you mean?  -@
  from (irb):16
  from /Users/davea/.rvm/gems/ruby-2.4.0@global/gems/railties-5.0.1/lib/rails/commands/console.rb:65:in `start'
  from /Users/davea/.rvm/gems/ruby-2.4.0@global/gems/railties-5.0.1/lib/rails/commands/console_helper.rb:9:in `start'
  from /Users/davea/.rvm/gems/ruby-2.4.0@global/gems/railties-5.0.1/lib/rails/commands/commands_tasks.rb:78:in `console'
  from /Users/davea/.rvm/gems/ruby-2.4.0@global/gems/railties-5.0.1/lib/rails/commands/commands_tasks.rb:49:in `run_command!'
  from /Users/davea/.rvm/gems/ruby-2.4.0@global/gems/railties-5.0.1/lib/rails/commands.rb:18:in `<top (required)>'
  from bin/rails:4:in `require'
  from bin/rails:4:in `<main>'

但我得到了

NoMethodError: undefined method `-' for "\xA0":String

您在上面看到的错误。

我不必使用正则表达式,但想不出其他任何东西可以让我替换一系列东西。

我使用的是 Ruby 2.4。

【问题讨论】:

  • 欢迎来到 Stack Overflow。请注意您的拼写和语法。 Stack Overflow 不是一个讨论列表,它是一个在线参考,这些东西确实很重要。如果您不这样做,我们必须解决这些问题,这会占用我们可以用来帮助他人的时间。

标签: ruby regex binary range


【解决方案1】:

假设您想用空格替换 ASCII 值 97 到 127 之间的字符:

irb(main):002:0> text = 'TeStInG'
=> "TeStInG"
irb(main):003:0> (97..127).each { |e| text.gsub!(e.chr,' ') }
=> 97..127
irb(main):004:0> text
=> "T S I G"

或者,您可以尝试以下方法:

irb(main):024:0> text.gsub(/[\x00-\x20]/, 'Z')
=> "TZSZIZG"

【讨论】:

  • 也许问 hte 很明显,但是为了让这个与我的示例一起工作,我是否使用 "(160..194).each { |e| text.gsub!(e.chr,' ' ) }"?
  • 是的,但也试试我的第二个版本。我相信它更接近您的初衷(也许更有效);只需使用所需范围的十六进制值即可。
  • 当我尝试使用“td_text.gsub(/[\xA0-\xC2]/, ' ')”的第二个解决方案时,它失败并出现错误“无效的多字节转义:/[\xA0- \xC2]/"。第一个解决方案也失败了,但出现错误“Encoding::CompatibilityError: incompatible character encodings: UTF-8 and ASCII-8BIT”
  • 我们开始涉猎这里,但是...ruby-doc.org/core-2.4.0/Encoding.html
  • 你可以强制编码为 ASCII-8Bit。
【解决方案2】:

随便用

str.tr("\xA0-\xC2", ' ')

使用十六进制的\x 转义序列。

或者如果字符码不是静态的

charset = [160.chr,194.chr].join('-')
str.tr(charset, ' ')

【讨论】:

  • 不幸的是,当我运行“td_text.tr("\xA0-\xC2", ' ')”时,我收到了错误“ArgumentError:UTF-8 中的无效字节序列”。当我将有问题的字符串输出到屏幕时,它占用了几行,但包含可见文本“?PLACE”。
  • 问题是"\xA0-\xC2"[160.chr,194.chr].join('-')正在生成8位ASCII,而Ruby现在默认为UTF-8。如何告诉 Ruby 使用 8 位 ASCII 包含在文档和互联网上的多个页面中。
  • 为什么投反对票?请解释一下,以便我改进答案。
【解决方案3】:

思考这个:

160.to_s(16) # => "a0"
194.to_s(16) # => "c2"

"a0""c2" 分别是 160 和 194 的十六进制表示。通常我们使用十六进制版本,因为小数会引起混淆。

您可以使用"\xa0""\u00a0",具体取决于您使用的是 8 位 ASCII、UTF-8 还是 Unicode。当前的 Ruby 默认为 UTF-8。

这是一个由要测试的字符范围组成的字符串:

text = ("\u00a0" .. "\u00c2").to_a.map(&:chr).join
# => " ¡¢£¤¥¦§¨©ª«¬­®¯°±²³´µ¶·¸¹º»¼½¾¿ÀÁÂ"

这是告诉 Ruby 修改该范围内的所有字符的方法:

text.gsub(/[\u00A0-\u00c2]/, ' ')
# => "                                   "

综上所述,我建议使用tr,如akuhn's answertr 为此目的更快。

【讨论】:

  • 不幸的是,如果我将变量设置为 'text = "\r\n \xA0PLACE \r\n "' 然后运行 ​​"text.gsub(/[\u00A0-\u00c2]/, ' ')”,我收到错误“ArgumentError:UTF-8 中的无效字节序列”。
  • 您可能需要阅读有关告诉 Ruby 使用 8 位 ASCII 或从 8 位 ASCII 转换为 UTF-8 的信息。
【解决方案4】:

试一试:

string = "\xA0"
string.gsub( /[\x00-\xFF]/, '' )
=> " "

这涵盖了 0x00(十进制 0)和 0xFF(十进制 255)之间的 ASCII 字符范围。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2016-07-10
    • 2012-08-18
    • 1970-01-01
    • 2017-09-20
    • 2020-07-23
    • 2013-11-26
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多