Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/asp.net/31.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C#asp.net将具有long属性的对象传递到前端会更改它';s值_C#_Asp.net_Asp.net Core_.net 5 - Fatal编程技术网

C#asp.net将具有long属性的对象传递到前端会更改它';s值

C#asp.net将具有long属性的对象传递到前端会更改它';s值,c#,asp.net,asp.net-core,.net-5,C#,Asp.net,Asp.net Core,.net 5,我正在构建一个带有react.js前端(尽管我相当确定这与问题无关)和asp.net后端(针对net5.0,不确定是否相关)的应用程序。当我调用后端API时,我得到一个对象,该对象部分包括它根据传入的数据生成的ID,该ID的类型为C#中的long(64位int)。我看到的行为是,C#中的变量和从前端响应读取的变量是不同的。它们似乎在大约16-17位之后漂移 这是预期的吗?有什么办法绕过它吗 复制我看到的内容/图片的代码: C# 控制台输出:ID在C#控制器方法:92233720306530550

我正在构建一个带有react.js前端(尽管我相当确定这与问题无关)和asp.net后端(针对net5.0,不确定是否相关)的应用程序。当我调用后端API时,我得到一个对象,该对象部分包括它根据传入的数据生成的ID,该ID的类型为C#中的long(64位int)。我看到的行为是,C#中的变量和从前端响应读取的变量是不同的。它们似乎在大约16-17位之后漂移

这是预期的吗?有什么办法绕过它吗

复制我看到的内容/图片的代码:

C#

控制台输出:
ID在C#控制器方法:9223372030653055062

Chrome开发工具:

当我试图访问前端的ID时,我得到了错误的ID,以000而不是062结尾

编辑1:有人建议这是因为JavaScript的
Number.MAX\u SAFE\u INTEGER
小于我传递的值。我不相信这是原因,但也许我错了,有人可以启发我。在JS方面,我使用的是
BigInt
,正是因为我传递的数字对于
number
来说太大了。问题是在我将结果解析为JS对象之前(除非Chrome自动这样做,导致问题中引用的图片)

编辑2:根据下面的答案,在我将值解析为BigInt之前,JS可能正在将值解析为一个数字,所以我仍然在丢失精度。更熟悉网络的人能证实这一点吗?

JavaScript引擎(显然)无法创建这么大的数字。尝试打开控制台并输入以下内容:

var myLong=9223372030653055062;

console.log(myLong)JavaScript将该值解释为一个64位浮点数。如果要保留该值,最好将其作为字符串传递回去

示例JS演示问题:

var值=9223372030653055062;
console.log(值);

console.log(type of(value))Javascript中数字的最大大小为2^53-1,即9007199254740991。在C#a long是2^64-1,这更大。所以“9223372030653055062”可以作为C#long,但不能作为JavaScript数字,因为它太大了。如果这个ID在使用long的数据库中使用,我建议您将它作为字符串传递给JavaScript。

尽管原因是这个数字比JS能够准确表示的要大,但您似乎被Chrome的开发工具预览分散了注意力。这只是一个“有用的”预览,不一定是事实

dev工具预览显示了响应的有用视图。我假设AJAX响应是使用application/json的内容类型传输的,因此Chrome将json解析为JS对象并让您预览响应。检查Response选项卡,这是AJAX代码实际接收到的内容

很有可能在您有机会对该数字使用
BigInt
之前就已经解析了JSON,从而限制了精度。您还没有向我们展示您的AJAX代码,所以这是我最好的猜测

唯一的解决方案是将其序列化为字符串,然后添加手动步骤将字符串转换为
BigInt

jsObject.generatedId = BigInt(jsObject.generatedId);

如果您使用它作为ID,那么您最好将其作为字符串保存在客户端,因为您不可能使用它进行任何计算。

我认为这是Javascript或Json格式的一个限制,您可以使用字符串而不是长字符串吗?
long.Parse()
是最慢的方法。使用
9223372030000000+rand。下一步(int.MaxValue)
同时,重新使用随机实例(使其成为静态成员)。这不仅是一个性能优化不足的问题,还可以确保您不会意外地使用同一个种子。@JoelCoehoorn忽略了实际的逻辑。这并不是ID的实际生成方式,只是一种说明问题的方法。在实际公式中没有Random()用法。@phuzi我编辑了我的问题,说我在前端使用BigInt,但也许JS仍然使用Number?我还不太熟悉web开发。如果在您有机会使用BigInt之前将响应解析为JS对象,那么该数字将已经转换为reglar JS数字,精度将降低。您可以调试AJAX请求/响应来确认这一点。是否没有办法告诉JS使用BigInt(据我推测,BigInt应该用Number来解决问题)?我很确定没有办法阻止浏览器这样做。OP的号码是9223372030653055000,远远大于您在9007199254740991时所声明的
号码的最大值,使得
号码的最大大小比2^53-1大得多
jsObject.generatedId = BigInt(jsObject.generatedId);