有没有比 C# 中的预处理器指令(#if 等)更好的东西?
Posted
技术标签:
【中文标题】有没有比 C# 中的预处理器指令(#if 等)更好的东西?【英文标题】:Is there something better than preprocessor directives (#if, etc) in C#? 【发布时间】:2019-07-09 19:28:47 【问题描述】:这种类型的大多数问题都试图改变程序行为(可以在运行时决定的事情)或者想要直接处理调试打印。这有点不同。
我的代码依赖于外围设备(如读卡器)。有时我不使用它,这意味着该库不存在。 (而且我很好,因为“库”原来意味着安装一个 2GB 的软件套件)。当我删除库时,我无法打开设备。如果我无法打开设备,我就无法创建使用它的类成员。由于类不起作用,我无法从代码中调用它的方法。因此,我不能只是选择不执行它;我需要它离开,因为没有库它就无法编译。
像#if
这样的预处理器指令以及所有这些都可以,也许;但是这些东西出现在多个文件中,这意味着在每个文件的顶部独立维护一个#define
。我来自一个更简单的地方(意思是 C),可以使用一个头文件来控制它。我注意到 C# 对 #define 相当敌对(标签是否存在;不允许使用常量或计算),这让我觉得还有另一种方法。
你是怎么处理的?
---跟进---
我确实阅读了“重复”的 Q/A,并且对我正在处理的内容有相当好的了解。我在最初的搜索中没有找到这些问题,但有时就是这样。
@Amy 建议顶部的#define 是“不是它是如何完成的”,而是“把它放在命令行上”。因此,(如果我意识到我们坚持使用这种机制)讨论可能会转向研究实现这一点的方法。一个人不会简单地下降到终端并这样做。它以“IDE 功能”或“IDE hacks”的形式出现。
@Alexei Levenkov 问我真正想要什么。我真的想(a)不出现编译错误,并且(b)通过有选择地省略代码来做到这一点。并且,找到与我建议的方式等效的 C#。 由于我很久没有使用 VS 或 C#,因此解决了更多的限制。所以我知道的比你们都少得多。考虑到我从最后一个人那里得到了代码并且必须处理我看到的东西,我不想让我之后的人去弄清楚我可能做了什么“有趣”的事情来让它工作。因此,诸如手动编辑项目文件之类的事情可能会奏效,但也会引起恐慌。
@ Eric Lippert 建议“敌对”确实是“明智的”。我的舌头可能在那个地方太深了。 VS 似乎在告诉我我做错了,所以我感觉到有一种我根本不知道的“正确方法”。至于支持2GB的应用程序,我会去各种计算机,拉下存储库并尝试一些东西,所以这个“开销”想随之传播。如果我通过手机链接进行下载,那就更糟了。如果我构建包含所有内容的应用程序,则最终用户需要在程序运行之前安装该软件套件。理论上,他们可能需要购买该软件。如果我给你发了一个井字游戏,并告诉你在你安装 Oracle 之前它不会运行,那么你可能会忽略整个事情。
我考虑了“将接口存根”的想法,但类中的钩子似乎比我想要处理的要多。另外,我不知道这些东西是做什么的,所以我必须对它们有所了解才能“伪造”它们。
最后我决定我们仍然主要使用#if 方案来完成这项工作,而我想象的替代功能可能存在,但实际上并没有。而且我正在使用@Jim G.引用的项目文件中的规定,因为它完成了工作并且只是有点不完美。已经足够好了。
【问题讨论】:
预处理器符号在命令行中传递给编译器或 MSBuild 的一部分。将它们放在每个文件的开头并不是这样做的。 部分课程可能是一个值得关注的策略。没多想,只是想出一个主意。 C# 项目文件实际上可以根据项目配置(使用Condition
属性)更改项目中包含的文件。据我所知,这并没有从 VS 中暴露出来,但它对大批量代码很有用。或者,创建一个 API 来抽象您为其编译不同版本的库,并在运行时(或编译时,此时无关紧要)换出整个程序集。这假设您有某种可以轻松删除的自然界面。
2GB 的存储成本为 4 美分;你为什么要担心微不足道的钱?您是否在某种资源极度受限的环境中工作?
你认为“敌对”的东西,很多人会认为是“明智的”。
【参考方案1】:
作为@BJ Safdie said here:
在您的编译属性或构建选项中设置它们。 您可以通过右键单击项目并选择构建选项 菜单中的属性。【讨论】:
这相当不错。唉,“解决方案”构建了两个项目,因此必须意识到它们都需要修改。不过,这比进入每个源文件要好得多!以上是关于有没有比 C# 中的预处理器指令(#if 等)更好的东西?的主要内容,如果未能解决你的问题,请参考以下文章
在 C# 的 #if 中使用 #define 预处理器指令是不是有效