为什么在这个简单的F#示例中未收集弱引用?

open System

let WeakReferenceExample() =
    let mutable obj = new Object();
    let weak = new WeakReference(obj);

    GC.Collect();
    Console.WriteLine("IsAlive: {0}\nobj <> null is {1}\n---",weak.IsAlive,obj <> null);

    obj <- null;
    GC.Collect();
    Console.WriteLine("IsAlive: {0}",weak.IsAlive);

WeakReferenceExample()
Console.ReadKey()

Rx In Action书本样本中翻译而来。上面的代码在运行时提供以下输出,与在C#中编译并运行它时得到的输出不同。

IsAlive: True
obj <> null is True
---
IsAlive: True

为什么不收集弱引用?

lhfeic 回答:为什么在这个简单的F#示例中未收集弱引用?

这是测量影响结果的情况之一。

根本原因是在调试过程中优化了编译器(反向?)以获取更好的本地语言。

撰写时:

let list1 = [1; 2; 3]
let list2 = [3; 4; 5]
printfn "%b" (list1 = list2)

这详细说明了每个子表达式:

let list1 = [1; 2; 3]
let list2 = [3; 4; 5] 
let list1' = list1
let list2' = list2
let is_eq = list1'.Equals(list2')
printfn "%b" (is_eq)

现在您可以开始猜测它的去向了。

 Console.WriteLine("IsAlive: {0}\nobj <> null is {1}\n---",weak.IsAlive,obj <> null);

致力于:

    let isAlive = weak.IsAlive
    let obj' = obj
    let isNotNull = obj' <> null
    Console.WriteLine("IsAlive: {0}\nobj <> null is {1}\n---",isAlive,isNotNull);

现在,当您这样做时:

    obj <- null;
    GC.Collect();

请注意,引用obj'中仍然存在。

因此,在GC传递期间将不会收集对象。 这就是WeakReference所显示的。

有趣的是,如果注释掉第一个Console.Writeline,则没有子表达式的详细说明,因此也没有引用,您将得到:

IsAlive: False

或者您也可以以发布模式构建它。

本文链接:https://www.f2er.com/2528657.html

大家都在问