zoukankan      html  css  js  c++  java
  • C# 在不同编译下的不同表现

      这是我在2018年的时候发在Unity Forums上的帖子, 至今无人回复, 之前是想用TypedReference做DataTable的相关功能的, 可是结果不正确.

    tiancaiwrkOct 18, 2018 

    System.TypedReference bugged? can't figure out how to use it !!!

    C# has some way to get Generic Type target pointer, such as GCHandle / Marshal,
    this time I want to use System.TypedReference for getting pointer of any struct, bug I think it's bugged...
    I dont know how to report a BUG to Unity, just post it here
    here is the code, it works in VS project but not unity project:
        void Start()
        {
            int v1 = 100;
            int v2 = 1000;
     
            var m1 = __makeref(v1);
            var m2 = __makeref(v2);
     
            var val1 = __refvalue(m1, int);     // val1 is 100
            var val2 = __refvalue(m2, int);     // val2 is 1000
     
            Debug.Log(val1);
            Debug.Log(val2);
     
            unsafe
            {
                *(IntPtr*)(&m1) = new IntPtr((void*)&v2); // 这里应该是把m1的值改变了的 m1应该为1000
     
                val1 = __refvalue(m1, int);     // val1 is 100 -- not changed 可是这里m1赋值没有变换, 还是100
                val2 = __refvalue(m2, int);     // val2 is 1000
     
                Debug.Log(val1);
                Debug.Log(val2);
     
                var ptr = *(IntPtr*)(&m1);
                var p = (int*)ptr.ToPointer();
                var data = *p;                  // data is 1000 -- changed 奇怪的是这里得到的m1的值又是1000
     
                Debug.Log(data);
            }
        }
    And what's more, if I dont Set the pointer of m1, the value of [data] is Strange!!
        void Start()
        {
            int v1 = 100;
            int v2 = 1000;
     
            var m1 = __makeref(v1);
            var m2 = __makeref(v2);
     
            var val1 = __refvalue(m1, int);     // val1 is 100
            var val2 = __refvalue(m2, int);     // val1 is 1000
     
            Debug.Log(val1);
            Debug.Log(val2);
     
            unsafe
            {
                var ptr = *(IntPtr*)(&m1);
                var p = (int*)ptr.ToPointer();
                var data = *p;                  // data is 536019728 [random] -- WTF 更奇怪的是直接取m1的值, 居然不对
     
                Debug.Log(data);
            }
        }
    This issue is happened in unity project, it works as expected in VS project.
    the VS project value is :
     
            static unsafe void TT()
            {
                int v1 = 100;
                int v2 = 1000;
     
                var m1 = __makeref(v1);
                var m2 = __makeref(v2);
     
                var val1 = __refvalue(m1, int);     // val1 is 100
                var val2 = __refvalue(m2, int);     // val2 is 1000
     
                unsafe
                {
                    *(IntPtr*)(&m1) = new IntPtr((void*)&v2);  // m1值被赋值1000
     
                    val1 = __refvalue(m1, int);     // val1 is 1000 VS工程编译的话, 这个m1值赋值正确的 1000
                    val2 = __refvalue(m2, int);     // val2 is 1000
     
                    var ptr = *(IntPtr*)(&m1);
                    var p = (int*)ptr.ToPointer();
                    var data = *p;                  // data is 1000 这里也是正确的
                }
            }

      这个也是偶然想到极限速度对变量赋值的时候看到的做法, 测试以后发现不对劲. 以前大部分时候程序出错我们都会先想到是自己代码写错了, 不过这里可以看出

    编译器也是有错的时候的......

  • 相关阅读:
    Python入门11 —— 基本数据类型的操作
    Win10安装7 —— 系统的优化
    Win10安装6 —— 系统的激活
    Win10安装5 —— 系统安装步骤
    Win10安装4 —— 通过BIOS进入PE
    Win10安装2 —— 版本的选择与下载
    Win10安装1 —— 引言与目录
    Win10安装3 —— U盘启动工具安装
    虚拟机 —— VMware Workstation15安装教程
    Python入门10 —— for循环
  • 原文地址:https://www.cnblogs.com/tiancaiwrk/p/11276111.html
Copyright © 2011-2022 走看看