debugging 是否可以让C#调试工具的[动态检视]节点为这个类别工作?

atmip9wb  于 2022-11-14  发布在  C#
关注(0)|答案(1)|浏览(127)

请考虑以下代码:

public class DynamicDictionary : DynamicObject, IDictionary<string, object?>
    {
        [DebuggerBrowsable(DebuggerBrowsableState.Never)]
        private ExpandoObject InnerObject = new ExpandoObject();

        public object? this[string key] {
            get {
                return ((IDictionary<string, object?>)InnerObject)[key];
            }

            set {
                ((IDictionary<string, object?>)InnerObject)[key] = value;
            }
        }

        public ICollection<string> Keys {
            get {
                return ((IDictionary<string, object?>)InnerObject).Keys;
            }
        }

        public ICollection<object?> Values {
            get {
                return ((IDictionary<string, object?>)InnerObject).Values;
            }
        }

        public int Count {
            get {
                return ((ICollection<KeyValuePair<string, object?>>)InnerObject).Count;
            }
        }

        public bool IsReadOnly {
            get {
                return ((ICollection<KeyValuePair<string, object?>>)InnerObject).IsReadOnly;
            }
        }

        public void Add(string key, object? value)
        {
            ((IDictionary<string, object?>)InnerObject).Add(key, value);
        }

        public void Add(KeyValuePair<string, object?> item)
        {
            ((ICollection<KeyValuePair<string, object?>>)InnerObject).Add(item);
        }

        public void Clear()
        {
            ((ICollection<KeyValuePair<string, object?>>)InnerObject).Clear();
        }

        public bool Contains(KeyValuePair<string, object?> item)
        {
            return ((ICollection<KeyValuePair<string, object?>>)InnerObject).Contains(item);
        }

        public bool ContainsKey(string key)
        {
            return ((IDictionary<string, object?>)InnerObject).ContainsKey(key);
        }

        public void CopyTo(KeyValuePair<string, object?>[] array, Int32 arrayIndex)
        {
            ((ICollection<KeyValuePair<string, object?>>)InnerObject).CopyTo(array, arrayIndex);
        }

        public IEnumerator<KeyValuePair<string, object?>> GetEnumerator()
        {
            return ((IEnumerable<KeyValuePair<string, object?>>)InnerObject).GetEnumerator();
        }

        public bool Remove(string key)
        {
            return ((IDictionary<string, object?>)InnerObject).Remove(key);
        }

        public bool Remove(KeyValuePair<string, object?> item)
        {
            return ((ICollection<KeyValuePair<string, object?>>)InnerObject).Remove(item);
        }

        public bool TryGetValue(string key, [MaybeNullWhen(false)] out object? value)
        {
            return ((IDictionary<string, object?>)InnerObject).TryGetValue(key, out value);
        }

        IEnumerator IEnumerable.GetEnumerator()
        {
            return ((IEnumerable)InnerObject).GetEnumerator();
        }

        public override bool TryGetMember(GetMemberBinder binder, out object? result)
        {
            return ((IDictionary<string, object?>)InnerObject).TryGetValue(binder.Name, out result);
        }

        public override bool TrySetMember(SetMemberBinder binder, object? value)
        {
            ((IDictionary<string, object?>)InnerObject)[binder.Name] = value;
            return true;
        }
    }

它实现了一个字典,其键可以像属性一样访问:

dynamic Vars = new DynamicDictionary();
    Vars.Test = "Something happened";

它运行正常,但调试器动态视图节点除外,该节点在展开时显示错误消息“无法计算表达式。不支持操作。未知错误:0x 80070057”的名称:

当然,展开“结果视图”会按预期工作。
现在我知道错误代码0x80070057E_INVALIDARG,但它并不能真正解释这里发生了什么。根据我在调试器表达式文档中找到的内容,它应该可以工作:
在[监看式]视窗中评估实作System.Dynamic.IDynamicMetaObjectProvider的对象时,会加入[动态检视]节点。[动态检视]节点会显示对象成员,但不允许编辑成员的值。
如果我从InnerObject中删除[DebuggerBrowsable(DebuggerBrowsableState.Never)],它自己的“动态视图”节点可以展开以显示值,而不会出现错误。
因此,问题是--我是否遗漏了一些覆盖,这些覆盖将在这里 Package InnerObject,以便调试器的Dynamic View节点在DynamicDictionary类示例上工作,如果是,是哪一个,或者由于某些调试器限制而根本不可能做到这一点?
我也愿意接受关于更好的问题标题的建议。

wz1wpwve

wz1wpwve1#

它相信如果你重写GetDynamicMemberNames,这是让“动态视图”工作的一个步骤。我还没有尝试过继承DynamicObject。相反,我在实现IDynamicMetaObjectProvider时遇到了这个问题。而且,对我来说,如果在阅读任何属性值时使用的任何内部逻辑出错,或者调用Debugger.NotifyOfCrossThreadDependency,这也可以阻止它显示任何值。

相关问题