Dart - 如果值不是分数,则 int.toDouble() 仍将 runTimeType 设为 int

Posted

技术标签:

【中文标题】Dart - 如果值不是分数,则 int.toDouble() 仍将 runTimeType 设为 int【英文标题】:Dart - int.toDouble() still makes the runTimeType as int if the value is not a fraction 【发布时间】:2021-05-16 12:43:56 【问题描述】:

飞镖版本 2.10.0

我正在使用带有 firestore 作为后端的 Flutter Dart,并且遇到了一个问题,当存储(在 json_seralizer 之后)到 double 类型的变量时,字段的值为 1,虽然成功,但它的运行时仍然是 int。

当将双变量值分配给另一个双变量时出现运行时错误,错误 type 'int' is not a subtype of type 'double?'在类型转换中

例如:- 在 Firestore -> 右值:1

在 Dart 类中 -> 双倍率值

通过序列化

rateValue = (rValue as num)?.toDouble()

然后,

double currencyExchangeRate;
currencyExchangeRate = rateValue //throws error at runtime type 'int' is not a subtype of type 'double?' in type cast

Dartpad示例代码看问题,

import 'dart:math' as math;
void main() 
 
  math.Random rand = math.Random();
  
  int x = rand.nextInt(10);
  
  double a = x.toDouble();
  double b = (x as num).toDouble();
  
  print ('a is $a and $a.runtimeType and b is $b and $b.runtimeType');
  


//Above code prints "a is 7 and int and b is 7 and int"

我已经搜索了很多关于相同问题的 *** 帖子,但到目前为止没有任何帮助。

即使使用显式转换并且没有动态变量,双变量(a 和 b)仍然显示 int 的运行时类型。

如何成功分配currencyExchangeRate = rateValue 并防止出现此运行时错误?

谢谢。

【问题讨论】:

问题在于你使用 DartPad。 DartPad 在 dart2js 上运行,这意味着所有代码在执行之前都会被转译成 javascript。在Javascript中,没有intdouble的概念,只有Number。我不确定,但是如果您对数字变量执行runtimeType,我的想法是如果它包含小数部分(或者是NaN 或无穷大),它将显示double,否则将显示int(基本上它只需在值上运行Number.isInteger)。但是,在 Dart 运行时中运行示例代码会显示预期的输出,其中 ab 的运行时类型为 double @Abion47 你是对的。我疯了,我颤动的飞镖代码中的问题是由于其他原因造成的。这是因为我使用的是我在 json_serializer 诞生之前自己编写的代码,并且该代码使用的是 Map<String, dynamic> map = Map<String, dynamic>.from(exchangeRatesSnapshot.data["toCurrency"]); Map<String, double> mapDouble = map.cast<String, double>(); 请注意我没有明确地执行 .toDouble() 而是 map.cast。我将发布我自己的问题的答案。感谢您的意见。 【参考方案1】:

我已经找到了我在自己的颤振飞镖代码中特别面临的问题的原因。

在 dart 中提供 json_serializer 之前,我自己手动将 firestore 数据转换为类,并且该代码未使用 .toDouble() 方法进行转换。因此,值 1 仍被视为整数而不是双精度值。

json_seralizer 使用 fromJson 和 toJson 方法创建的分部类正确地将图 1 转换为目标类中的 double。

我已经删除了我自己的序列化程序代码,现在在这种情况下依赖 json_serializer 生成的代码(无论如何我总是这样做)。

所以,dart 转换没有真正的问题,只是我在调查中的疏忽,我没有发现我自己很久以前的序列化程序代码是罪魁祸首的事实。

Json_seralizer 执行(e as num)?.toDouble(),它正确地将目标类中的 1 转换为 1.0。

【讨论】:

以上是关于Dart - 如果值不是分数,则 int.toDouble() 仍将 runTimeType 设为 int的主要内容,如果未能解决你的问题,请参考以下文章

分类--阈值

埃及分数

Dart是值传递还是引用传递

多分类SVM损失函数: Multiclass SVM loss

LeetCode 856. 括号的分数

1447. 最简分数