如何在.NET中指定控制台应用程序的退出代码?


471

我在.NET中有一个简单的控制台应用程序。它只是大型应用程序的测试部分。我想指定控制台应用程序的“退出代码”。我该怎么做呢?

Answers:


599

3种选择:

  • Main如果声明Main要返回的方法,则可以从中返回它int
  • 您可以致电Environment.Exit(code)
  • 您可以使用属性设置退出代码:Environment.ExitCode = -1;。如果没有其他设置返回代码或使用上述其他选项之一的情况,将使用此方法。

根据您的应用程序(控制台,服务,Web应用程序等),可以使用不同的方法。


12
对于那些想知道为什么在这种情况下不起作用的人,请确保将项目编译为“控制台应用程序”而不是“ Windows应用程序”。
Marcel Gosselin 2012年

9
如果我有一个带有某些参数的WinForms应用程序,我希望它表现为控制台应用程序怎么办?
sebagomez 2012年

5
您也可以只将maine程序键入为int(用int替换void)并使用例如“ return -1;”。从主程序返回。这比Environment.Exit()(取决于环境)更具可移植性。
werner 2013年

14
@DannyBeckett按照惯例,退出代码0表示成功,而非零表示失败。return;通过退出代码指示成功0,并return -1;指示失败。
allonhadaya

6
您还可以使用以下属性设置退出代码:Environment.ExitCode = -1;
t3b4n

270

除了回答return int的答案外,还...出于理智。请在枚举中定义您的退出代码,并在适当的地方加上Flags。它使调试和维护变得非常容易(而且,此外,您可以在帮助屏幕上轻松打印出退出代码-您确实有其中之一,对吗?)。

enum ExitCode : int {
  Success = 0,
  InvalidLogin = 1,
  InvalidFilename = 2,
  UnknownError = 10
}

int Main(string[] args) {
   return (int)ExitCode.Success;
}

46
您可能想补充一点,“成功”的“ 0”值不是偶然的,而实际上是该情况的“标准”值。
Christian.K,

39
这个。这就是为什么SO是互联网历史上最伟大的网站。这些建议在任何教科书中都很难找到,只能通过与经验丰富的专业人员交谈来收集。谢谢。
Daniel Szabo 2012年

17
您说0是成功的标准值,但是将0/1转换为布尔值时,0为false,1为true!可能更准确地说退出代码为0表示“无错误”,而不是“成功”,因为退出代码是ErrorResult,而不仅仅是结果。
马克·夏皮罗

11
有关Microsoft约定的完整列表,请参见msdn.microsoft.com/zh-cn/library/windows/desktop/…。一些人列出了大量的const,并在下面的注释中将其用于切换案例。
nawfal

5
@MarkShapiro,我猜想0 = Success是这样的事实:仅需要一个成功代码,但是许多错误代码(例如,计算机整数中没有+或-的0可以用来唯一地标识成功)
Sebastian,2014年

49

您可以使用三种方法从控制台应用程序返回退出代码。

  1. 修改Main应用程序中的方法,以使其返回int而不是void(在VB.Net 中返回Integer而不是的函数Sub),然后从该方法返回退出代码。
  2. Environment.ExitCode属性设置为退出代码。请注意,方法1.具有优先权-如果该Main方法返回的其他值voidSub在VB.Net中为),则将忽略此属性的值。
  3. 将退出代码传递给Environment.Exit方法。与其他两种方法相反,这将立即终止该过程。

应该遵守的一个重要标准是0代表“成功”。

在相关主题上,请考虑使用枚举定义应用程序将要返回的退出代码。该的FlagsAttribute将允许您返回码的组合。

另外,请确保您的应用程序被编译为“控制台应用程序”。


1
这提出了一个有趣的观点。设置Environment.ExitCode不会立即Environment.Exit关闭程序,但是方法会立即关闭程序
PsychoData

1
退出代码也适用于Windows应用程序。如果应用程序将通过c#通过Process对象启动,则可以要求该对象访问WaitForExit(),然后向其请求退出代码。
Nyerguds 2014年

43

如果要使用David建议的方法,还应该查看[Flags]属性。

这使您可以对枚举执行按位操作。

[Flags]
enum ExitCodes : int
{
  Success = 0,
  SignToolNotInPath = 1,
  AssemblyDirectoryBad = 2,
  PFXFilePathBad = 4,
  PasswordMissing = 8,
  SignFailed = 16,
  UnknownError = 32
}

然后

(ExitCodes.SignFailed | ExitCodes.UnknownError)

将是16 +32。:)


3
这意味着程序将说“您的密码错误”,然后继续尝试对其进行签名,并仅在失败后才停止。一旦失败,您应该返回。别的是一个警告,该计划应该还是返回0
皮特Kirkham的

3
鲜为人知的事实是[Flags]不执行任何操作来启用或禁用按位操作。它所做的只是重写ToString方法,以便输出表示按位标志。使用或不使用它,您仍然可以执行按位运算。
史蒂文

3
@Steven知道这很高兴,但是我仍然建议使用该属性装饰用于“标志用法”的枚举,如果没有其他传达意图的话。
MarioDS

25
int code = 2;
Environment.Exit( code );

17
您不只是出于技术原因写了“ Environment.Exit(2);”。?
Blorgbeard在

52
将魔术数字分配给名称毫无意义的变量不会使魔术变少。
Blorgbeard将于


11

只需从main返回适当的代码即可。

int main(string[] args)
{
      return 0; //or exit code of your choice
}

2
默认的C#控制台应用程序根本不声明main。它宣布 static void Main(string[] args);
Mark Lakata

19
@Mark Lakta:然后更改它,不是吗?
Esteban Araya

11

如果您的主体具有无效的返回签名,请使用ExitCode,否则,您需要通过返回的值对其进行“设置”。

Environment.ExitCode属性

如果Main方法返回void,则可以使用此属性设置将返回到调用环境的退出代码。如果Main不返回void,则将忽略此属性。此属性的初始值为零。


8

作为Scott Munro 答案的更新:

  • 在C#6.0和VB.NET 14.0(VS 2015)中,需要Environment.ExitCodeEnvironment.Exit(exitCode)从控制台应用程序返回非零代码。更改的返回类型Main无效。
  • 在F#4.0(VS 2015)中,将考虑main入口点的返回值。

关于C#6的第一点可以验证吗?我似乎无法在网上找到任何东西。Main函数的返回值附加到进程的退出代码上(至少在所有以前的编译器中),为什么他们应该对此进行更改?
阿曼·麦克希塔里安

纯粹的轶事证据,但是我只是在自己的库中遇到了这个问题,在该库中,仅仅从中返回结果/错误代码Main()并没有设置Process.ExitCode调用应用程序所看到的。
马库斯·曼格斯多夫

MSDN认为int Main仍然可以用作Environment.ExitCode的替代方法。 链接
Arman McHitarian '16

我有一个运行多个线程的应用程序。在某些情况下,我需要在退出应用程序之前通过Thread.Abort()破坏某些线程。在这种情况下,请使用int Main(){... thread.Abort(); ... return 0;}不会导致进程退出代码为0:进程退出代码为-1。在某些情况下,MS似乎决定使用主线程的返回值设置进程的退出代码的约定对他们来说还不够好。公平地说,这可能是时间问题:线程中止可能会在游戏后期设置退出代码。
David I. McIntosh

7

枚举选项非常好,但是可以通过将数字乘以来改进,如下所示:

enum ExitCodes : int
{
  Success = 0,
  SignToolNotInPath = 1,
  AssemblyDirectoryBad = 2,
  PFXFilePathBad = 4,
  PasswordMissing = 8,
  SignFailed = 16,
  UnknownError = 32
}

如果出现多个错误,将特定的错误编号加在一起将为您提供一个唯一的编号,该编号代表检测到的错误的组合。

例如,错误级别6只能由错误4和2组成,12只能由错误4和8组成,14只能由2、4和8等组成。


2
但是,如果遇到一个错误,您却不愿意检查其他错误。大多数应用程序没有。
Nyerguds 2014年


0

使用此代码

Environment.Exit(0);

如果您不想返回任何内容,请使用0作为int。


这不是回答OP的问题,返回0表示返回的东西...
PL
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.