引用程序集中的条件编译

本文关键字:条件 编译 集中 程序 程序集 引用 | 更新日期: 2023-09-27 18:28:29

我正在编写一个程序集,其中包含一些有条件编译的成员,例如:

[Conditional("DEBUG")]
public static void Log(string message) { /*...*/ }

这样使用:

public void DoStuff() {
    Log("This will only appear on debug builds");
    /* ... Do stuff ... */
}

但是,当我把这个程序集交给某人在他们的项目中使用时,我希望他们能够定义是否编译DEBUG条件成员。

如果这是不可能的(例如,方法在编译时被完全删除),那么有没有任何方法可以打包一个程序集的多个"配置"(例如,可能使用[AssemblyConfiguration]),并根据引用程序集的配置选择它们?

此外:我不想寻求在引用程序集的.csproj文件中手动设置引用的建议;我知道我可以做到,但这很乏味,而且必须为每一个参考都做。

引用程序集中的条件编译

[Conditional("DEBUG")]正是您想要的。MSDN对该属性的解释是:

向编译器指示,除非定义了指定的条件编译符号,否则应忽略方法调用或特性。

然而,该解释(以及许多其他解释)没有提到的是,有问题的编译符号需要在引用程序集中定义。换句话说,如果Assembly A包含方法

[Conditional("DEBUG")]
public static void SomeMethod()
{ /* ... */ }

并且将该程序集编译为Release,则只要该程序集被编译为Debug就将从Assembly B调用SomeMethod

这些方法将独立于定义的值编译成程序集,因此您可以使用这些方法,并且方法的使用将取决于编译客户端程序集时编译器的定义。

换句话说,System.Diagnostics.ConditionalAttribute指示编译器应忽略METHOD CALL,而不是如何编译该方法。

当一些其他代码尝试使用方法时,方法调用将在编译时删除。

因此,根据你的目标,你可以:

  • 如果你想让其他人有条件地使用你的"Log"方法,但你自己在该程序集中的代码不应该使用该方法-给出发布程序集(一个在没有"DEBUG"的情况下编译的程序集)
  • 如果您希望其他人也有条件地使用您的"日志"和您自己的代码进行日志记录,请提供调试程序集
  • 如果您希望能够在运行时为自己的代码打开/关闭日志记录,请考虑使用允许它的实际日志记录框架(即使是.Net框架的一部分也允许这样做)

有关更多信息,请查看条件属性