Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/261.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/visual-studio/8.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 未调用Main(字符串[]args)方法_C#_Visual Studio_Visual Studio 2017 - Fatal编程技术网

C# 未调用Main(字符串[]args)方法

C# 未调用Main(字符串[]args)方法,c#,visual-studio,visual-studio-2017,C#,Visual Studio,Visual Studio 2017,我正在使用Visual Studio 2017 每当我按下F5开始调试我的程序时,我注意到program类中的Main(string[]args)方法不会被调用,即使program中的字段已初始化,如下面的屏幕截图所示: 在创建TcpClient实例并将其分配给相应字段后,调试器从未触及我在Main(string[]args)方法上设置的断点 为了确定,我已经将项目的启动对象设置为程序类。这并没有解决问题: 我错过了什么 编辑: 我在我的Main方法中添加了Console.WriteLine

我正在使用Visual Studio 2017

每当我按下
F5
开始调试我的程序时,我注意到
program
类中的
Main(string[]args)
方法不会被调用,即使
program
中的字段已初始化,如下面的屏幕截图所示:

在创建
TcpClient
实例并将其分配给相应字段后,调试器从未触及我在
Main(string[]args)
方法上设置的断点

为了确定,我已经将项目的启动对象设置为
程序
类。这并没有解决问题:

我错过了什么

编辑:

我在我的
Main
方法中添加了
Console.WriteLine(“输入主方法…”)
,但在我开始调试时,它不会打印到控制台

实际上,在创建
TcpClient
实例之后没有发生任何事情(或者说,没有立即可见的事情)——没有抛出异常;程序不会自动终止;控制台保持空白

编辑:

结果表明,
TcpClient
构造函数内部正在发生崩溃。

在这种情况下,静态字段初始值设定项(程序类)不应包含可能抛出或超时的代码

问题中的高位代码是静态字段初始值设定项。这将在第一次访问类型时运行。如果初始值设定项或静态构造函数阻塞或抛出,则应用程序将在不调用
Main
的情况下终止。这意味着不能使用任何错误处理代码来捕获这些异常

这种有保证的顺序使得在C#中实现简单的单例非常容易。由于保证了执行顺序,因此不需要双重锁定。查看Jon Skeet关于以下内容的文章:

这就足以创建线程安全的单例

静态字段初始值设定项,在这种情况下(程序类)不应包含可能抛出或超时的代码

问题中的高位代码是静态字段初始值设定项。这将在第一次访问类型时运行。如果初始值设定项或静态构造函数阻塞或抛出,则应用程序将在不调用
Main
的情况下终止。这意味着不能使用任何错误处理代码来捕获这些异常

这种有保证的顺序使得在C#中实现简单的单例非常容易。由于保证了执行顺序,因此不需要双重锁定。查看Jon Skeet关于以下内容的文章:


这就足够创建线程安全的单例了

请记住,
TcpClient(string,int)
构造函数在该点()打开一个新连接:

初始化TcpClient类的新实例并连接到指定主机上的指定端口。

此构造函数创建一个新的TcpClient,并尝试与提供的主机名和端口号进行同步连接

如果复制/粘贴您的代码(插入我自己的
RemoteServerIpAddressString
),则当应用程序尝试构建
TcpClient
时,我会看到它挂起。如果我在此时中断调试器,我可以看到它卡在试图连接到远程计算机的
System.Net.Sockets.Socket.DoConnect

一段时间后,它放弃,抛出一个异常,然后抛出一个
TypeInitializationException
,这会破坏调试器

这与您的观察相符:

实际上,TcpClient实例创建后没有发生任何事情(或者说,没有立即可见的事情)——没有抛出异常;程序不会自动终止;控制台保持空白

此时,
TcpClient
仍在尝试连接。在成功之前,该类型永远不会被初始化,并且在此之前,将永远不会运行
Main
。如果你让它保持足够长的时间,它可能会失败,就像我的一样

如果我确保
TcpClient
连接到打开的端口,则
TcpClient
构造函数立即完成,并运行
Main


在静态构造函数中执行长时间运行的操作(尤其是网络操作)是一个非常糟糕的主意。CLR需要在初始化类型时获取锁,这会停止初始化其他类型,并可能导致死锁

您可能希望在
Main
方法中构造
TcpClient
,或者将其构造为:

private static readonly TcpClient TcpClient = new TcpClient();
然后主要是:

TcpClient.Connect(...);

请记住,
TcpClient(string,int)
构造函数在该点()打开一个新连接:

初始化TcpClient类的新实例并连接到指定主机上的指定端口。

此构造函数创建一个新的TcpClient,并尝试与提供的主机名和端口号进行同步连接

如果复制/粘贴您的代码(插入我自己的
RemoteServerIpAddressString
),则当应用程序尝试构建
TcpClient
时,我会看到它挂起。如果我在此时中断调试器,我可以看到它卡在试图连接到远程计算机的
System.Net.Sockets.Socket.DoConnect

一段时间后,它放弃,抛出一个异常,然后抛出一个
TypeInitializationException
,这会破坏调试器

这与您的观察相符:

实际上,TcpClient实例创建后没有发生任何事情(或者说,没有立即可见的事情)——没有抛出异常;程序不会自动终止;控制台保持空白

此时,
TcpClient
仍在尝试连接。在成功之前,该类型永远不会被初始化,并且在此之前,将永远不会运行
Main
。如果你让它保持足够长的时间,它可能会失败,就像我的一样

如果我是妈妈
TcpClient.Connect(...);