IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 开发工具 -> 十六 C# 调试程序相关技术 -> 正文阅读

[开发工具]十六 C# 调试程序相关技术

1、预处理指令

  • 在编译软件时,常会出现两个版本,如一个基本版本,一个高级版本,这就要用到预处理指令。

  • 使用预处理指令可以进制编译器编译代码的某一部分,还可以进制编译器与而外功能相关的代码。

  • C#中没有单独的预处理器,由编译器直接进行预处理

  • 预处理指令都是以#开始例如:

  • #defing和undef:

    • 不包含实际意义,单独使用无任何作用
    • 必须用在程序的开头,并且在其他任何关键字之前,例如用在命名空间声明中的那些指令之前,否则会报下图错误
    • 与#if、 #elif 、#else联合使用才有意义
      在这里插入图片描述
      在这里插入图片描述
  • #if #elif #else 和#endif

    • 告诉编译器是否要对某段代码执行边沿
# define debug  //声明
# define Release
//# undef debug   // 取消声明
# undef Release
using System;

namespace _1_预处理指令1
{
    class Program
    {
        static void Main(string[] args)
        {
#if (!debug) && Release

            Console.WriteLine("只存在发布版本");
#elif debug && Release
            Console.WriteLine("同时存在两个版本,这是不被允许的");
#elif debug && (!Release)
            Console.WriteLine("只存在调试版本");
#else
            Console.WriteLine("两个版本都不存在");
#endif
            Console.ReadLine();

        }
    }
}

  • #waring和#error
    使用这两个指令可以检查#defing是否出错,使用#warning语句还可以提醒自己做过的事
    在这里插入图片描述
    在这里插入图片描述
# define debug  //声明
# define Release
//# undef debug   // 取消声明
# undef Release
using System;

namespace _1_预处理指令1
{
    class Program
    {
        static void Main(string[] args)
        {
#if (!debug) && Release

            Console.WriteLine("只存在发布版本");
#elif debug && Release
#error 调试版本与发布版本同时存在,不被允许
            Console.WriteLine("同时存在两个版本,这是不被允许的");
#elif debug && (!Release)
            Console.WriteLine("只存在调试版本");
#warning 现在是调试版本,发布时请切换成发布版本
#else
            Console.WriteLine("两个版本都不存在");
#endif
            Console.ReadLine();

        }
    }
}

  • #region和#endregion

    • 将一段代码标记给任意指定的一个块,可被编译器死别,让程序可读性更高
      在这里插入图片描述
  • #line

    • 用于改变编译器在警告和错误信息中显示的文件名和行号信息
    • 恢复默认行号的方式:# line default
      在这里插入图片描述
      在这里插入图片描述
      在这里插入图片描述
      在这里插入图片描述
# define debug  //声明
# define Release
//# undef debug   // 取消声明
# undef Release
using System;

namespace _1_预处理指令1
{
    class Program
    {
        static void Main(string[] args)
        {
            #region 此程序块主要是#if #elif #else 和#endif的实例
#if (!debug) && Release

            Console.WriteLine("只存在发布版本");
#elif debug && Release
#error 调试版本与发布版本同时存在,不被允许
            Console.WriteLine("同时存在两个版本,这是不被允许的");
#elif debug && (!Release)
            Console.WriteLine("只存在调试版本");
#line 200
#warning 现在是调试版本,发布时请切换成发布版本
#warning test1
#warning test2
#line default
#warning test3

#else
            Console.WriteLine("两个版本都不存在");
#endif
            Console.ReadLine();
            #endregion
        }
    }
}

在这里插入图片描述

  • #pragma
    可以抑制或恢复指定的编译警告
    • disable :抑制
    • restore :恢复
    • 可省去 CS
# define debug  //声明
# define Release
//# undef debug   // 取消声明
# undef Release
using System;

namespace _1_预处理指令1
{
    class Program
    {
        static void Main(string[] args)
        {

            #region 此程序块主要是#if #elif #else 和#endif的实例
#pragma warning disable CS1030
#if (!debug) && Release

            Console.WriteLine("只存在发布版本");
#elif debug && Release
#error 调试版本与发布版本同时存在,不被允许
            Console.WriteLine("同时存在两个版本,这是不被允许的");
#elif debug && (!Release)
            Console.WriteLine("只存在调试版本");
#line 200
#warning 现在是调试版本,发布时请切换成发布版本
#warning test1
#warning test2
#line default
#warning test3

#else
            Console.WriteLine("两个版本都不存在");
#endif
            Console.ReadLine();
            #endregion

            //#pragma warning disable     //后面不跟代码代表抑制此预处理指令后面的所有警告(前面的警告不起作用)
#pragma warning disable CS0219   // 带CS的错误编码
#pragma warning disable  0168   // 可以省略警告的CS只写编号
            int a = 0;
            int b = 10;
#pragma warning restore   //恢复默认设置
            int c = 100;
            int[] myint;
            Console.WriteLine(b);
            Console.ReadLine();

        }
    }
}

非中断调试

生成应用程序时,解决方案的配置有两种

  • Debug(默认)
  • Release
  • 在debug配置下生成应用程序,不仅仅是运行编写好的代码,调试程序包含了应用程序的符号信息,VS知道执行每行代码时发生了什么。符号信息可匹配已编译的机器代码应用程序中现有的值,而机器代码程序包含人么抑郁读取的信息。此类信息包含在.pdb文件中,这些文件位于计算机的Debug目录下。

在这里插入图片描述

在这里插入图片描述

在这里插入图片描述
在这里插入图片描述

Debug与Release两种模式

  • Debug
    • 向IDE输出调试信息
    • 在执行应用程序期间查看作用域内变量的值
    • 暂停程序和重启程序
    • 在代码的某个位置自动暂停程序的执行
    • 一次执行程序中的一行代码
    • 见识变量的变化
    • 修改变量的内容
    • 测试函数的调用
  • 在Release配置中,编译器会优化应用程序代码,不执行这些操作,同时发布版本运行的比较快,完成了应用程序开发后,一般应给用户提供发布版本,因为发布版本不需要调试版本所包含的符号信息
  • 即使选择了Release时,也会生成扩展名为.vshost.exe和.pdb的文件

*.vshost.exe和*.pdb

  • .pdb文件:程序数据库文件(Program Database File) 默认设置下:
    • Debug的PDB是full,保存着调试和项目状态信息,有断言、堆栈检查等代码,可以对程序的调试配置进行增量链接。
    • Release的PDB制定为pdb-only,保存着程序出了什么错误,以及错误在哪些行
  • .vshost.exe文件 宿主进程文件(VS host process)是visulal studio 中的一项功能,主要是为了提高调试性能。Release时最好删除。
  • .vshost.exe.manifest文件:
    • 是一个以.manifest为后缀的XML文件,由于组织和描述割裂应用程序以及并行组件,用于COM类、接口及库的绑定和激活,而这些信息,以往都是存储在注册表中的
    • Manifests也指定了组件程序集的文件及Windows类,Release时也最好删除。

不生成*.pdb与 *.vshost.exe的方法

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

输出窗口两种模式

调试:debug
生成:build
Debug.WriteLine()、Trace.WriteLine()需要引入命名空间:using System.Diagnostics;
Debug.WriteLine()、Trace.WriteLine()和Console.WriteLine()区别

  • Debug.WriteLine()在debug模式下运行,甚至不能编译为可发布的程序,Release版本中不会执行
  • Trance.WrtieLine()还可用于发布程序,Release和Debug两种模式下都可以做被执行
  • Console.WriteLine():输出在控制台上,而以上两种是在输出窗口输出,
  • Debug.WriteLine()与Console.WriteLine()使用完全一样,只是输出的方式不同。
  • Trance.WriteLine()只能使用字符串拼接的方式Trance.WriteLine(“字符串1”+i+“字符串2”),不能使用TranceWriteLine(“字符串1{0}字符串2”,i)的方式
  • Trance.WriteLine()还可以使用Trance.WriteLine(“字符串1”+i+“字符串2”, “行数”)
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

在这里插入图片描述

  • 插入跟踪点

Visual Studio调试器指南—断点和跟踪点
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述

断点调试

写好应用程序以后,可以采用两种方式执行:调试模式、非调试模式
调试模式(遇到断点停止)和非调试模式(忽略断点继续执行)区别

断点是调试器设置的一个代码位置。当程序运行到断点时,程序中断执行,回到调试器。断点时最常用的技巧。调试时,只有设置了断点并使程序回到调试器,才能对程序进行在线调试(程序运行过程中调试)。
设置断点:鼠标、快捷菜单、快捷方式(F9)、条件断点
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

开始调试:
调试方式:

  • 逐过程(F10):逐过程语句将过程调用语句当做一条普通语句,不会进入方法体内(方法体内语句不会逐句执行)
  • 逐句(F11):如果直接从按F11将从Main方法(程序入口点)开始逐条语句执行,每按一次F11执行一条语句。如果是按启动程序运行到断点处后停止,再按F11,没按一次执行一条语句
  • 跳出(Shift+F11)
  • 继续(F5):跳转到下一个断点
  • 设置下一语句(Ctrl+Shift+F10):程序运行到断点后停止,如果需要跳过某些语句,直接执行到指定的语句,则需要通过设置下一条语句来实现。

在这里插入图片描述

  • 显示下一句(Alt+*)

断点调试之停止

停止:

  • 全部中断(Ctrl+Alt+Break):可以停止死循环,跳出死循环,执行死循环的下一条语句
  • 停止程序执行(Shift+F5):停止程序执行,完全中断程序

条件断点:

  • 条件
  • 操作
    在这里插入图片描述

在这里插入图片描述
运行到指定位置
在这里插入图片描述

断点标签

断点处
断点窗口
作用:批量设置断点,搜索中设置

在这里插入图片描述
在这里插入图片描述

数据便签

数据便签是应用程序调试期间用于查看对象和变量的一种高级便签消息。当调试器执行到断点时,将鼠标移动到对象或者变量上方时,你会看到他们的当前值。
在这里插入图片描述

局部变量窗口

失效的局部吧变量不在显示
在这里插入图片描述

自动窗口

只显示当前断点程序运行处相关的变量。即使全局变量,只要给当前断点运行不想关也不显示。
局部变量窗口:显示的是当前运行程序所有有效的变量,因为全局变量始终有效,所以全局变量会始终显示。局部变量运行失效后就不在局部变量窗口显示。

在这里插入图片描述

监视窗口

在这里插入图片描述

调用堆栈

监视调用的方法
在这里插入图片描述

查看定义(F12)

将鼠标定位到相关函数方法上,按F12

即时窗口

可用于查看相应变量当前值,也可以临时调整变量响应的值
在这里插入图片描述

  开发工具 最新文章
Postman接口测试之Mock快速入门
ASCII码空格替换查表_最全ASCII码对照表0-2
如何使用 ssh 建立 socks 代理
Typora配合PicGo阿里云图床配置
SoapUI、Jmeter、Postman三种接口测试工具的
github用相对路径显示图片_GitHub 中 readm
Windows编译g2o及其g2o viewer
解决jupyter notebook无法连接/ jupyter连接
Git恢复到之前版本
VScode常用快捷键
上一篇文章      下一篇文章      查看所有文章
加:2022-03-10 22:48:06  更:2022-03-10 22:50:32 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 6:46:34-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码