向大数字添加逗号是否有轨道技巧?

Jes*_*ess 194 ruby ruby-on-rails

有没有办法让rails打印出一个带逗号的数字?

例如,如果我有一个数字54000000.34,我可以运行<%= number.function%>,这将打印出"54,000,000.34"

谢谢!

Joh*_*ley 339

你想要这个number_with_delimiter方法.例如:

<%= number_with_delimiter(@number, :delimiter => ',') %>
Run Code Online (Sandbox Code Playgroud)

或者,您可以使用该number_with_precision方法确保始终以两位小数位数显示数字:

<%= number_with_precision(@number, :precision => 2, :delimiter => ',') %>
Run Code Online (Sandbox Code Playgroud)

  • 我相信默认情况下,分隔符是逗号,所以在这种情况下你不需要传递该选项. (9认同)
  • @Mo这是一个视图辅助方法.您应该能够通过在模块中包含`ActionView :: Helpers :: NumberHelper`从模块中使用它. (5认同)
  • 注意:`number_with_delimiter` 过于复杂且速度非常慢,调用堆栈的深度非常大。它使用 `i18n` 能够格式化人类和外星文明已知的任何数字(或者可能只是选择 `,` 或 `.` 作为十进制数字,即使你将其指定为参数)。它分配了数千个对象(因此其性能模式很复杂且难以分析)。如果您不需要根据语言环境支持不同的数字格式设置方式,请考虑仅使用正则表达式。 (4认同)
  • 您应该关闭分隔符,以便当前区域设置可以决定使用什么.这允许正确显示使用分隔符的句点的语言环境,而不是将它们认为小数点的数字放在数千个之间.请参阅下面的coloradoblue答案. (3认同)
  • Rails 4 语法:&lt;%= number_with_precision(@number, precision: 0, delimiter: ',') %&gt; (2认同)

pgu*_*rio 128

对于没有使用rails的人:

number.to_s.reverse.gsub(/(\d{3})(?=\d)/, '\\1,').reverse
Run Code Online (Sandbox Code Playgroud)

  • 当然,它会反转字符串,然后在3个数字序列之后添加一个逗号,后面跟着另一个数字,然后将其反转. (7认同)
  • 尼斯.而你的回答似乎是*微小*(只有一秒钟超过一百万次迭代)比[here](http://www.rubyquiz.com/quiz113.html)所提出的方法更快:`number.to_s. reverse.scan.(?/?(?:\ d*\)\ d {1,3} - /)加入( '')reverse` (2认同)
  • 这很好,但它不适用于小数. (2认同)
  • @pguardiario \\ 1中的额外\是什么?不是'\ 1`足够吗?谢谢. (2认同)

Pat*_*and 29

是的,使用NumberHelper.您正在寻找的方法是number_with_delimiter.

 number_with_delimiter(98765432.98, :delimiter => ",", :separator => ".")
 # => 98,765,432.98
Run Code Online (Sandbox Code Playgroud)


Ale*_*sky 20

如果要在视图外添加逗号而不想包含某些模块,可以使用number_to_delimited方法(rails version> = 4.02).例如:

#inside anywhere
ActiveSupport::NumberHelper.number_to_delimited(1000000) # => "1,000,000"
Run Code Online (Sandbox Code Playgroud)


col*_*lue 19

如果你做了很多,但也因为上面没有暗示它是FYI,Rails有合理的默认number_with_delimiter方法.

#inside controller or view
number_with_delimiter(2444323.4)
#=> 2,444,323.30

#inside console
helper.number_with_delimiter(233423)
#=> 233,423
Run Code Online (Sandbox Code Playgroud)

如果您以最典型的方式进行分配,则无需提供分隔符值.


cho*_*boy 18

无论有没有Rails,这样做的直接方法是:

require 'active_support/core_ext/numeric/conversions'

12345.to_s(:delimited)      # => "12,345"
12345.6789.to_s(:delimited) # => "12,345.6789"
Run Code Online (Sandbox Code Playgroud)

有关更多选项,请参阅Active Support Core Extensions - 数字 - 格式.

  • 通过此包含,您也可以使用“ActiveSupport::NumberHelper.number_to_delimited”。这个答案值得更多的赞成。 (2认同)
  • 我猜这在某些版本中发生了变化,但现在似乎应该是 .to_fs(:delimited) 。 (2认同)

fxf*_*mxf 15

对于那些不使用处理小数的rails的人来说更好的方法:

parts = number.to_s.split('.')
parts[0].gsub!(/(\d)(?=(\d\d\d)+(?!\d))/, "\\1,")
parts.join('.')
Run Code Online (Sandbox Code Playgroud)

如果你想要一个不同的分隔符,改变正则表达式中的最后一个','.

对于奖金,这是正则表达式的工作方式:

  • gsub用传递给gsub的第二个参数替换与正则表达式匹配的所有内容.在这种情况下\\1.\\1\1时评估所述第一捕获组正则表达式匹配.在这个正则表达式中(\d).
  • (\d)(?=(\d\d\d)+)匹配一个数字后跟一个或多个3位数组.第一组parens是我们的\1捕获组,第二组是\2.如果我们只是留下它我们会得到: 123456.gsub!(/(\d)(?=(\d\d\d)+)/, "\\1,") #=> 1,2,3,456这是因为1234场比赛,2345场比赛和3456场比赛所以我们在1,2和3之后放了一个逗号.
  • 通过添加(?!\ d),我们匹配之前不在数字之前的任何内容,因此(\d)(?=(\d\d\d)+(?!\d))意味着匹配一个数字,后面跟着一个数字,后跟一个数字.这样做的原因是gsub将继续替换匹配字符串的东西.如果我们只是替换第一场比赛,那么对于像123456789这样的数字,我们将获得123456,789.由于123456,789仍然匹配我们的正则表达式,我们得到123,456,789.

这是我得到代码的地方:https://github.com/rails/rails/blob/master/activesupport/lib/active_support/number_helper.rb#L298-L300

这里是我了解该正则表达式中正在发生的事情的地方:http://www.tutorialspoint.com/ruby/ruby_regular_expressions.htm