Ios 为什么不';在Xcode中触发断点的变异成员?

Ios 为什么不';在Xcode中触发断点的变异成员?,ios,swift,xcode,debugging,lldb,Ios,Swift,Xcode,Debugging,Lldb,在阅读Xcode或LLDB的文档时,我遇到了一些我似乎无法理解的问题。当应用程序到达具有断点的行时,在我看来,如果存在断点,LLDB应该在该行中断。在执行变异函数时访问该行代码不会触发断点的情况下 考虑以下示例: class DataSource { private init(){ data = [] for i in 0..<10 { data.append(i) // mutating func }

在阅读Xcode或LLDB的文档时,我遇到了一些我似乎无法理解的问题。当应用程序到达具有断点的行时,在我看来,如果存在断点,LLDB应该在该行中断。在执行变异函数时访问该行代码不会触发断点的情况下

考虑以下示例:

class DataSource {

    private init(){

        data = []

        for i in 0..<10 {

            data.append(i) // mutating func
        }
    }

    static let sharedInstance = DataSource()

    var data: [Int]! // Set a breakpoint on this line
}

class Worker {

    func work(){

        print("Append item")

        DataSource.sharedInstance.data.append(23) // mutating func

        print("Get first item")

        print(DataSource.sharedInstance.data[0]) // subscript - TRIGGERS BREAKPOINT

        print("Drop first")

        print(DataSource.sharedInstance.data.dropFirst()) // func - TRIGGERS BREAKPOINT

        print("Remove first")

        print(DataSource.sharedInstance.data.removeFirst()) // mutating func

        print("Remove at 0")

        print(DataSource.sharedInstance.data.remove(at: 0)) // mutating func
    }
}
类数据源{
私有init(){
数据=[]

对于macOS上的i in 0..,断点解析为:

(lldb) break list
Current breakpoints:
1: source regex = "Set a breakpoint", exact_match = 0, locations = 3, resolved = 3, hit count = 3
  1.1: where = mutable`mutable.DataSource.(in _788A7EC739C0395377AC3966BEDD9D35).init() -> mutable.DataSource + 40 at mutable.swift:15, address = 0x0000000100001b08, resolved, hit count = 1 
  1.2: where = mutable`mutable.DataSource.data.getter : Swift.ImplicitlyUnwrappedOptional<Swift.Array<Swift.Int>> + 80 at mutable.swift:15, address = 0x0000000100001e00, resolved, hit count = 2 
  1.3: where = mutable`mutable.DataSource.data.setter : Swift.ImplicitlyUnwrappedOptional<Swift.Array<Swift.Int>> + 96 at mutable.swift:15, address = 0x0000000100001e70, resolved, hit count = 0 
(lldb)中断列表
当前断点:
1:source regex=“设置断点”,精确匹配=0,位置=3,已解析=3,命中计数=3
1.1:where=mutable`mutable.DataSource.(在788A7EC739C0395377AC3966BEDD9D35中)。init()->mutable.DataSource+40 at mutable.swift:15,地址=0x0000000100001b08,已解析,命中计数=1
1.2:where=mutable`mutable.DataSource.data.getter:Swift.ImplicitlyUnwrappedOptional+80 at mutable.Swift:15,地址=0x0000000100001e00,已解析,命中计数=2
1.3:where=mutable`mutable.DataSource.data.setter:Swift.ImplicitlyUnwrappedOptional+96 at mutable.Swift:15,地址=0x0000000100001e70,已解析,命中计数=0
这是有意义的,“数据”ivar的定义产生了setter、getter和init方法,这些函数与此行相关联

但是,如果您查看可变访问的代码,例如append调用,则不会使用这些方法,相反,程序集如下所示:

(lldb) dis -c 5 -s 0x10000203b
mutable`Worker.work():
    0x10000203b <+235>: callq  0x100002cf0               ; type metadata accessor for mutable.DataSource at mutable.swift
    0x100002040 <+240>: movq   %rax, -0xf0(%rbp)
    0x100002047 <+247>: callq  0x100001d50               ; mutable.DataSource.sharedInstance.unsafeMutableAddressor : mutable.DataSource at mutable.swift
    0x10000204c <+252>: movq   (%rax), %rax
    0x10000204f <+255>: movq   %rax, %rcx
(lldb)dis-c5-s0x10000203b
可变'Worker.work():
0x10000203b:callq 0x100002cf0;在mutable.swift处为mutable.DataSource键入元数据访问器
0x100002040:movq%rax,-0xf0(%rbp)
0x100002047:callq 0x100001d50;mutable.DataSource.sharedInstance.UnsafemeutableAddressor:mutable.DataSource at mutable.swift
0x10000204c:movq(%rax),%rax
0x10000204f:movq%rax,%rcx
它正在通过类型元数据访问它将要更改的变量。这是一个通用函数,不会由“数据”ivar的定义触发,因此它不会被分配到该定义行。该访问必须知道它可以跳过getter或setter,但您必须让其他人解释它为什么会这样做


如果您对此感到好奇,您可以尝试将您的问题重新表述为关于Swift对数据访问的选择,更熟悉该语言实现的人可能会参与进来。

在macOS上,您的断点解析为:

(lldb) break list
Current breakpoints:
1: source regex = "Set a breakpoint", exact_match = 0, locations = 3, resolved = 3, hit count = 3
  1.1: where = mutable`mutable.DataSource.(in _788A7EC739C0395377AC3966BEDD9D35).init() -> mutable.DataSource + 40 at mutable.swift:15, address = 0x0000000100001b08, resolved, hit count = 1 
  1.2: where = mutable`mutable.DataSource.data.getter : Swift.ImplicitlyUnwrappedOptional<Swift.Array<Swift.Int>> + 80 at mutable.swift:15, address = 0x0000000100001e00, resolved, hit count = 2 
  1.3: where = mutable`mutable.DataSource.data.setter : Swift.ImplicitlyUnwrappedOptional<Swift.Array<Swift.Int>> + 96 at mutable.swift:15, address = 0x0000000100001e70, resolved, hit count = 0 
(lldb)中断列表
当前断点:
1:source regex=“设置断点”,精确匹配=0,位置=3,已解析=3,命中计数=3
1.1:where=mutable`mutable.DataSource.(在788A7EC739C0395377AC3966BEDD9D35中)。init()->mutable.DataSource+40 at mutable.swift:15,地址=0x0000000100001b08,已解析,命中计数=1
1.2:where=mutable`mutable.DataSource.data.getter:Swift.ImplicitlyUnwrappedOptional+80 at mutable.Swift:15,地址=0x0000000100001e00,已解析,命中计数=2
1.3:where=mutable`mutable.DataSource.data.setter:Swift.ImplicitlyUnwrappedOptional+96 at mutable.Swift:15,地址=0x0000000100001e70,已解析,命中计数=0
这是有意义的,“数据”ivar的定义产生了setter、getter和init方法,这些函数与此行相关联

但是,如果您查看可变访问的代码,例如append调用,则不会使用这些方法,相反,程序集如下所示:

(lldb) dis -c 5 -s 0x10000203b
mutable`Worker.work():
    0x10000203b <+235>: callq  0x100002cf0               ; type metadata accessor for mutable.DataSource at mutable.swift
    0x100002040 <+240>: movq   %rax, -0xf0(%rbp)
    0x100002047 <+247>: callq  0x100001d50               ; mutable.DataSource.sharedInstance.unsafeMutableAddressor : mutable.DataSource at mutable.swift
    0x10000204c <+252>: movq   (%rax), %rax
    0x10000204f <+255>: movq   %rax, %rcx
(lldb)dis-c5-s0x10000203b
可变'Worker.work():
0x10000203b:callq 0x100002cf0;在mutable.swift处为mutable.DataSource键入元数据访问器
0x100002040:movq%rax,-0xf0(%rbp)
0x100002047:callq 0x100001d50;mutable.DataSource.sharedInstance.UnsafemeutableAddressor:mutable.DataSource at mutable.swift
0x10000204c:movq(%rax),%rax
0x10000204f:movq%rax,%rcx
它正在通过类型元数据访问它将要更改的变量。这是一个通用函数,不会由“数据”ivar的定义触发,因此它不会被分配到该定义行。该访问必须知道它可以跳过getter或setter,但您必须让其他人解释它为什么会这样做

如果您对此感到好奇,您可以尝试将您的问题重新表述为Swift对数据访问的选择,更熟悉该语言实现的人可能会加入进来