Skip to content

Commit b79d617

Browse files
xedinjakepetroules
authored andcommitted
[SWUtil] PropertyListItem: Clarify use of init overloads that take array and dictionary
The original comment that these overloads can be removed was incorrect because the existential of `PropertyListItemConvertible` doesn't self conform. The overloads are still needed to support collections with heterogeneous values but nothing else and so they should be disfavored. Turns out that some of the expressions that used to take advantage of these overloads only work due to the solver producing a valid solution from the "diagnostic" mode. For example: ``` public var propertyListItem: PropertyListItem { return .init(entries .sorted { $0.identifier < $1.identifier } .map { [ "bundle-id": .plString($0.identifier), "tags": PropertyListItem($0.tags.sorted()), "bundle-path": .plString($0.path.str), ] }) } ``` This expression should have been ambiguous because it can match both `.init(any ...)` and `.init([any ...])` overloads due to an existential conversion that is bi-directional for the closure. For `.init(any ...)`, result of the closure is going to be erased to existential inside of the body of the `.map` closure and for `.init([any ...])`, this erasure is going to happen outside but both are equally valid.
1 parent dd63fb6 commit b79d617

File tree

1 file changed

+11
-3
lines changed

1 file changed

+11
-3
lines changed

Sources/SWBUtil/PropertyList.swift

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -362,16 +362,24 @@ extension Dictionary: PropertyListItemConvertible where Key == String, Value: Pr
362362
}
363363

364364
public extension PropertyListItem {
365-
init(_ x: any PropertyListItemConvertible) {
365+
init<T>(_ x: T) where T: PropertyListItemConvertible {
366366
self = x.propertyListItem
367367
}
368368

369-
// Will remove this with rdar://problem/44204273
369+
/// This overload is intended only to support arrays with heterogeneous values.
370+
/// For example: ["", 42] can be represented as [any PropertyListItemConvertible]
371+
/// but `any PropertyListItemConvertible` doesn't actually conform to
372+
/// `PropertyListItemConvertible` hence we cannot use the overload above.
373+
@_disfavoredOverload
370374
init(_ x: [any PropertyListItemConvertible]) {
371375
self = .plArray(x.map{$0.propertyListItem})
372376
}
373377

374-
// Will remove this with rdar://problem/44204273
378+
/// This overload is intended only to support dictionaries with heterogeneous values.
379+
/// For example: ["q": "", "a": 42] can be represented as [String: any PropertyListItemConvertible]
380+
/// but `any PropertyListItemConvertible` doesn't actually conform to
381+
/// `PropertyListItemConvertible`.
382+
@_disfavoredOverload
375383
init(_ x: [String: any PropertyListItemConvertible]) {
376384
self = .plDict(x.mapValues { $0.propertyListItem })
377385
}

0 commit comments

Comments
 (0)