tnblog
首页
视频
资源
登录

C#6.0-7.3 unsafe 不安全块的使用

4856人阅读 2019/8/28 17:40 总访问:3470539 评论:0 收藏:0 手机
分类: Win32

unsafe关键字相信很多朋友都没有用到过

今天特此来讲一下


1.在unsafe中可以调用指针这是非常重要的一点


   1   简单的案例:


  1. static int Main(string[] args)
  2. {
  3.     int i = 0;
  4.     unsafe
  5.     {
  6.         int* ip = &i;
  7.         Console.WriteLine("scroce i address:{0:x} value:{1}", (int)ip, i);
  8.     }
  9. }


案例过程:

    (1) 可以看到我们用一个指针变量ip把 int 类型 i 的指针给存起来了

    (2) 然后将其指针 ip 和  i 的值打印了出来


案例结果:


   2   string和结构体使用的案例:


  1. struct People
  2. {
  3.     public int Id;
  4.     unsafe public char* Name;
  5.     unsafe public char* Remark;
  6. }
  7. //或 注意类是不能使用的
  8. unsafe struct PeopleTwo
  9. {
  10.     public int Id;
  11.     public char* Name;
  12.     public char* Remark;
  13. }
  14. //主方法
  15. static void Main(string[] args)
  16. {
  17.     string therename = "hb";
  18.     string thereRemark = "patter good";
  19.     unsafe
  20.     {
  21.         //第一部分 开始
  22.         fixed(char* charname = therename)
  23.         {
  24.             Console.WriteLine("New scroce remark address:0x{0:x} ,And the value is {1}", (int)charname,*charname);
  25.         }
  26.         //第一部分 结束
  27.         //第二部分 开始
  28.         Console.WriteLine("next is People struct");
  29.         People per = new People();
  30.         per.Id = 4;
  31.         People* p = &per;
  32.         fixed (char* twoName = therename, tworemark = therename)
  33.         {
  34.             //赋值操作
  35.             p->Name = twoName;
  36.             p->Remark = tworemark;
  37.             //然后
  38.             Console.WriteLine("The struct p address:0x{0:x} ", (int)p);
  39.             Console.WriteLine("And port 'Name' address is 0x{0:x},value is {1}", (int)p->Name,*p->Name);
  40.             Console.WriteLine("And port 'Remark' address is 0x{0:x},value is {1}", (int)p->Name, *p->Name);
  41.         }
  42.         //第二部分 结束
  43.     }
  44. }


案例过程:

    第一部分:

        (1) 首先声明 therename 和 thereRemark 变量

        (2) 然后到unsafe不安全块中,定义一个 charname 的字符指针变量进行接收

        (3) 然后进行输出 指针地址 与 值

        (4)我们可以发现这个值只输出了一个字符,因为这里存储的是 char 类型的指针变量,所以一个指针只对应一个字符

        后面会讲如何全部输出!!!


【Note】:fixed 我的理解是让 char* 接收到 string 的特殊方法


    第二部分:

        (1) 我们声明了一个 People结构体变量 per 并用一个 p 的同结构指针去接收

        (2) 然后用 twoName 与 tworemark 字符指针分别去接收 therenamethereRemark

        (3) 最后赋值给机构 p ,然后对其进行输出


案例结果:



2.处理指针字符变量转string类型


   1   在这里我写了一个简单的方法:


  1. static void Main(string[] args)
  2. {
  3.     string therename = "hb";
  4.     string thereRemark = "patter good";
  5.     unsafe
  6.     {
  7.         People per = new People();
  8.         per.Id = 4;
  9.         People* p = &per;
  10.         SetValue(p, therename, thereRemark);
  11.     }
  12. }
  13. unsafe public static void SetValue(People* p, string name, string remark)
  14. {
  15.     fixed (char* therename = name, thereremark = remark)
  16.     {
  17.         Console.WriteLine("scroce name address:{0:x}", (int)therename);
  18.         Console.WriteLine("scroce remark address:{0:x}", (int)thereremark);
  19.         p->Name = therename;
  20.         p->Remark = thereremark;
  21.         Console.WriteLine("new name address:{0:x}", (int)(p->Name));
  22.         Console.WriteLine("new remark address:{0:x}", (int)(p->Remark));
  23.         string newname = GetString(p->Name);
  24.         Console.WriteLine($"variable newname value is:{newname}");
  25.         string newremark = GetString(p->Remark);
  26.         Console.WriteLine($"variable newname value is:{newremark}");
  27.     }
  28. }
  29. //处理指针字符变量转string类型
  30. unsafe public static string GetString(char* one)
  31. {
  32.     StringBuilder str = new StringBuilder();
  33.     if (one == null)
  34.     {
  35.         return "";
  36.     }
  37.     char** text = &one;
  38.     {
  39.         while (*text != null)
  40.         {
  41.             if (**text == '\0')
  42.             {
  43.                 break;
  44.             }
  45.             str.Append(**text);
  46.             *text = ++(*text);
  47.         }
  48.     }
  49.     return str.ToString();
  50. }


案例分析:

    主要将一下GetString()

        首先我要知道字符串是一个字符的数组组成的。

        通过 text 二级指针去获取指针变量 one 的指针,循环判断指针是否为空,如果不为空着用 StringBuilder循环添加起来,

        当返回值为 '\0' 着表示该指针已经走完了,最后返回结果


案例结果:


3.c/c++扩展




   1   maclloc的使用与声明:

  1. People* p2 = stackalloc People[1];


说明:我们知道在 c/c++中,声明动态内存并分配到到站的函数是 maclloc

          所以在这里我们可以用 stackalloc 来进行直接创建



如有更多关注请访问:https://docs.microsoft.com/zh-cn/dotnet/csharp/language-reference/language-specification/unsafe-code


谢谢!





欢迎加群讨论技术,1群:677373950(满了,可以加,但通过不了),2群:656732739

评价
这一世以无限游戏为使命!
排名
2
文章
635
粉丝
44
评论
93
docker中Sware集群与service
尘叶心繁 : 想学呀!我教你呀
一个bug让程序员走上法庭 索赔金额达400亿日元
叼着奶瓶逛酒吧 : 所以说做程序员也要懂点法律知识
.net core 塑形资源
剑轩 : 收藏收藏
映射AutoMapper
剑轩 : 好是好,这个对效率影响大不大哇,效率高不高
ASP.NET Core 服务注册生命周期
剑轩 : http://www.tnblog.net/aojiancc2/article/details/167
ICP备案 :渝ICP备18016597号-1
网站信息:2018-2025TNBLOG.NET
技术交流:群号656732739
联系我们:contact@tnblog.net
公网安备:50010702506256
欢迎加群交流技术