Set之后,Get为null,暂时没想明白。
特此补充:
提一下该问题的临时解决方案是将_lastSelectedPrimitive置为static模式。
原本该属性是缩写方式({get;private set;}),因为诡异幽灵的出现,方便测试追踪拆开为background field方式。
有所怀疑过的地方:
new MenuItemEx("置顶(_T)",SystemCommands.置顶,(sender, args) => { windowMain.CurrentCanvas.LastSelectedPrimitive?.MoveToTopMost(); },(sender, args) => { args.CanExecute = !(windowMain.CurrentCanvas.LastSelectedPrimitive != null && windowMain.CurrentCanvas.LastSelectedPrimitive.IsTopMost);}),
但原则上但凡是这个体系代码即便在我未知的情况下篡改该属性,那么应该也应该走Set过程。
也考虑过Fody是否有影响,然而细思着实没有,包括用标记消除影响。
我测试过放弃属性Set用法,改为一个函数(private SetLastSelectedPrimitive(PrimitiveBase pritivebase) ),均为此现象,直到将其static后执行的结果符合了预期逻辑。
一度对引用的认知产生人生的怀疑,这算是第二次的sharp代码幽灵(职业生涯还有一次是变量名的灵异事件,这么看都是对的,但结果就是不对,直到把变量名改了——结果对了)。
对此番诡异的代码过程扔出,望园友参与之讨论之。
该诡异,本人反复小心查看,未防止自己的不小心多次调用到Set,也改变名称,让其编辑时报错,以便查看...等等,谨慎对待该问题。特此补充调用引用图:
对于该诡异问题的测试,也一度拆分简写的红色标记部分,然而过程流程结果一样。
有网友提到多线程,即使是多线程也应该符合预期逻辑输出结果,何况乎这是视图类,是不会存在这种问题的。
注意最后一幅图是现在已经正常的截图——已经变更为static后,程序正常。
也需要特别注意我的评论,一旦F5启动后结果是正常的,那么程序的结果就会符合逻辑预期,但是是概率性的,只要F5启动后结果不正常,那么程序结果才不会符合预期。体现到菜单的Enable上,当然正是因为这里发现不正常,所以才这么慢慢拆开去Trace,去各个环节分析。
个人目前还是感觉应该是 WPF Command 模块的引发的问题,但是这块体系比较庞大,尚不清楚框架具体问题出现在何方。去掉static,去掉菜单(也就是整体去掉Command),直接在set输出get结果比较正常(至少没有不符合预期)。有知情者告知。
去掉Menu(Command)后,比如如下追踪结果正常:
public PrimitiveBase LastSelectedPrimitive { get { Trace.WriteLine($"_lastSelectedPrimitive Getter : {_lastSelectedPrimitive}"); return _lastSelectedPrimitive; } private set { _lastSelectedPrimitive = value; Trace.WriteLine($"_lastSelectedPrimitive Writer : {_lastSelectedPrimitive}"); Trace.WriteLine($"LastSelectedPrimitive Getter : {LastSelectedPrimitive}"); } }
望知情者告知。
是不是用了多线程
感谢你的参与讨论
首先排除底层问题,那么就是你的代码问题,那多半就是你修改了 私有字段_lastSelectedPrimitive,你查找下代码是否有哪里调用了。根据日志排除有动属性
为什么要排除“底层问题”?
我大致认为是WPF Command的问题。职业之路也偶尔发现MS出问题,至于mono之流则更甚(一个程序为此记了一页的坑和bug)。
感觉应该是 Command实现 不仅仅是走c#代码实现,有点像走指针(指针的指针)直接指向的 引用名 造成了问题,这样也就是解释了static会正常。但是尚不清楚,如何在command中可以处理掉这个问题,而不是用static去影响代码结构设计去跳过该问题。
疑问细节继续存在,大致Command 实现原理通过挖掘有了一些了解,因此有了从Command 去消除此Bug的方法。
在Command.CanExecute中还有更诡异的,直接用参数windowMain引用虽然偶尔不正常,但用Menu成员WindowMain也可以正常(暂无发现异常。后来继续测试出现了异常)。
只要不在Command.CanExecute调用windownMain.CurrentCanvas.LastSelectedPrimitive,那么正常,只要调用就可能异常,用static _lastSelectedPrimitive实现LastSelectedPrimitive正常。
Command带来的“怪异”甚是奇葩
已经改过一次变量名——曾经经历过一次,改名字ok的经历。
– 花飘水流兮 4年前最要命的是,时而运行正常(只要F5正常,就完全正常);根据F5的概率出现。
– 花飘水流兮 4年前虽然暂时解决了此问题,但该问题是个幽灵一般,没想通。
– 花飘水流兮 4年前这是在跟我开玩笑,我在指望它出现null的这段时间...高概率不出现~~
– 花飘水流兮 4年前