2

我试图在 Visual Studio 即时窗口中运行一些相当简单的代码。代码所做的只是从文件中读取一些 JSON 输入,并使用它来调用其他一些方法,以加载带有值的数据库。这是代码块:

using Newtonsoft.Json.Linq;
using System;
using System.IO;

namespace POST.API
{
    public class Initialization
    {
        public const string JSON_DATA_FILE = "C:\\OHA_SDD_POST_Development\\POST\\POST.API\\Services\\Setup\\InitializationData.json";
        public const string JSON_OBJKEY_DOMAIN = "Domain";
        public const string JSON_OBJKEY_ACCOUNTDOMAINTYPE = "AccountDomainType";
        public const string JSON_OBJKEY_ORGLOCTYPE = "OrganizationLocationType";

        public JObject POSTDataInitJObject;

        public JArray Domains;
        public JArray AccountDomainRoles;
        public JArray OrganizationLocationTypes;

        public API.Services.Domain SvcDomain;
        public API.Services.Organization SvcOrganization;
        public API.Services.Location SvcLocation;
        /// <summary>
        /// 
        /// </summary>
        /// <param name="JsonDataFile"></param>
        public Initialization(string JsonDataFile = JSON_DATA_FILE)
        {
            string JsonData = File.ReadAllText(JsonDataFile);
            POSTDataInitJObject = JObject.Parse(JsonData);

            Domains = (JArray)POSTDataInitJObject[JSON_OBJKEY_DOMAIN];
            AccountDomainRoles = (JArray)POSTDataInitJObject[JSON_OBJKEY_ACCOUNTDOMAINTYPE];
            OrganizationLocationTypes = (JArray)POSTDataInitJObject[JSON_OBJKEY_ORGLOCTYPE];
        }
        /// <summary>
        /// 
        /// </summary>
        public void Load()
        {
            LoadDomains();
            LoadOrganizationLocationTypes();
        }
        /// <summary>
        /// 
        /// </summary>
        /// <param name="Replace"></param>
        public void LoadDomains(bool Replace = true)
        {
            SvcDomain = new API.Services.Domain();

            if (Replace)
            {
                SvcDomain.ClearAllDomains(true);
            }

            foreach (var i in Domains)
            {
                SvcDomain.AddDomain(new API.Models.Domain
                {
                    Code = (string)i["Code"],
                    Definition = new API.Models.TypeDefinition
                    {
                        Name = (string)i["Name"],
                        Description = (string)i["Description"],
                        Order = Int32.Parse((string)i["Order"])
                    }
                });
            }
        }
        /// <summary>
        /// 
        /// </summary>
        /// <param name="Replace"></param>
        public void LoadOrganizationLocationTypes(bool Replace = true)
        {
            SvcLocation = new API.Services.Location();

            if (Replace)
            {
                SvcLocation.ClearAllOrganizationLocationTypes();
            }

            foreach (var i in OrganizationLocationTypes)
            {
                SvcLocation.AddOrganizationLocationType(new API.Models.OrganizationLocationType
                {
                    Definition = new API.Models.TypeDefinition
                    {
                        Name = (string)i["Name"],
                        Description = (string)i["Description"],
                        Order = Int32.Parse((string)i["Order"])
                    }
                });
            }
        }
    }
}

我可以在即时窗口中成功实例化该对象,但是当我尝试在该实例上调用该 Load() 方法时,我得到:

在 mscorlib.dll 中发生了“System.Threading.ThreadAbortException”类型的第一次机会异常

评估需要一个线程临时运行。使用 Watch 窗口执行评估。

我已经关闭了选项 -> 调试 -> 启用属性评估和其他隐式函数调用。

让我难住了......看起来超级简单,我完全无法克服它。

4

2 回答 2

4

您正在直接或间接调用其中包含以下内容的一些代码:

System.Diagnostics.Debugger.NotifyOfCrossThreadDependency()

为什么代码会有那个?

你们中的一些人可能遇到过这种情况,您尝试在调试期间评估属性或方法,并在手表的值单元格中获取此消息:
在此处输入图像描述

这个问题有一个快速的“解决方法”。如果你仔细看,你会在消息后看到一个小圆形图标: 在此处输入图像描述

按下此图标将强制评估继续,这很可能会给你你想要的结果:
在此处输入图像描述

当我们中断调试器并尝试评估需要运行代码的属性时,我们只能在当前线程中运行代码。所有其他线程都被冻结以最大程度地减少系统状态影响……但是,如果我的属性需要另一个线程来运行以完成评估怎么办?例如,如果我正在执行远程调用,我很可能需要 ThreadPool 线程来执行此操作……但所有其他线程都被冻结……这将导致“死锁”。调试器有一个保护措施,它可以让评估代码运行最多 5 秒。如果代码没有在时间限制内完成运行,例如,当我们由于线程冻结而被阻塞时,手表将被“挂起”5秒,之后评估将被中止。我们将收到此消息以通知我们该问题: 在此处输入图像描述

因此,该行代码会导致您收到以下消息:

调试器不会自动允许它,以避免状态更改,而是会给用户“函数评估需要所有线程运行”消息。

如果您打开了调试器,则:

如果用户认为可以让所有线程运行,他可以推送消息旁边的图标,这将导致调试器第二次运行属性代码,这次是所有线程都运行,并且不会在 NotifyOfCrossThreadDependency 方法上中止.

请阅读这篇文章了解更多详情。

另外,我不确定您在即时窗口中运行所有代码的理由是什么。也许您可以编写一个小型控制台应用程序并运行该应用程序。

于 2017-02-13T23:10:25.217 回答
0

所以,看起来这个问题是一个偶然的问题。我只是没有在我试图运行代码的项目中提供对 EntityFramework 的引用。不知道为什么它会抛出给定的错误,但这就是发生的事情。对我来说似乎很奇怪,但我会接受的。现在可以了。

于 2017-02-14T17:57:09.180 回答