@@ -322,7 +322,7 @@ impl ast::IntNumber {
322322
323323 pub fn float_value ( & self ) -> Option < f64 > {
324324 let ( _, text, _) = self . split_into_parts ( ) ;
325- text. parse :: < f64 > ( ) . ok ( )
325+ text. replace ( '_' , "" ) . parse :: < f64 > ( ) . ok ( )
326326 }
327327}
328328
@@ -361,7 +361,7 @@ impl ast::FloatNumber {
361361
362362 pub fn value ( & self ) -> Option < f64 > {
363363 let ( text, _) = self . split_into_parts ( ) ;
364- text. parse :: < f64 > ( ) . ok ( )
364+ text. replace ( '_' , "" ) . parse :: < f64 > ( ) . ok ( )
365365 }
366366}
367367
@@ -397,6 +397,15 @@ mod tests {
397397 assert_eq ! ( IntNumber { syntax: make:: tokens:: literal( lit) } . suffix( ) , expected. into( ) ) ;
398398 }
399399
400+ fn check_float_value ( lit : & str , expected : impl Into < Option < f64 > > + Copy ) {
401+ assert_eq ! ( FloatNumber { syntax: make:: tokens:: literal( lit) } . value( ) , expected. into( ) ) ;
402+ assert_eq ! ( IntNumber { syntax: make:: tokens:: literal( lit) } . float_value( ) , expected. into( ) ) ;
403+ }
404+
405+ fn check_int_value ( lit : & str , expected : impl Into < Option < u128 > > ) {
406+ assert_eq ! ( IntNumber { syntax: make:: tokens:: literal( lit) } . value( ) , expected. into( ) ) ;
407+ }
408+
400409 #[ test]
401410 fn test_float_number_suffix ( ) {
402411 check_float_suffix ( "123.0" , None ) ;
@@ -437,6 +446,14 @@ mod tests {
437446 check_string_value ( r"\nfoobar" , "\n foobar" ) ;
438447 check_string_value ( r"C:\\Windows\\System32\\" , "C:\\ Windows\\ System32\\ " ) ;
439448 }
449+
450+ #[ test]
451+ fn test_value_underscores ( ) {
452+ check_float_value ( "3.141592653589793_f64" , 3.141592653589793_f64 ) ;
453+ check_float_value ( "1__0.__0__f32" , 10.0 ) ;
454+ check_int_value ( "0b__1_0_" , 2 ) ;
455+ check_int_value ( "1_1_1_1_1_1" , 111111 ) ;
456+ }
440457}
441458
442459impl ast:: Char {
0 commit comments