@@ -970,6 +970,8 @@ static void determineBestChoicesInContext(
970
970
971
971
bool hasArgumentCandidates = false ;
972
972
bool isOperator = isOperatorDisjunction(disjunction);
973
+ bool isNilCoalescingOperator =
974
+ isOperator && isOperatorNamed(disjunction, " ??" );
973
975
974
976
for (unsigned i = 0 , n = argFuncType->getNumParams (); i != n; ++i) {
975
977
const auto ¶m = argFuncType->getParams ()[i];
@@ -1603,6 +1605,20 @@ static void determineBestChoicesInContext(
1603
1605
double bestCandidateScore = 0 ;
1604
1606
llvm::BitVector mismatches (argumentCandidates[argIdx].size ());
1605
1607
1608
+ // `??` is overloaded on optionality of the second parameter,
1609
+ // prevent ranking the argument candidates for this parameter
1610
+ // if there are candidates that come from failable initializer
1611
+ // overloads because non-optional candidates are always going
1612
+ // to be better and that can skew the selection.
1613
+ if (isNilCoalescingOperator && argIdx == 1 ) {
1614
+ if (llvm::any_of (argumentCandidates[argIdx],
1615
+ [](const auto &candidate) {
1616
+ return candidate.fromInitializerCall &&
1617
+ candidate.type ->getOptionalObjectType ();
1618
+ }))
1619
+ continue ;
1620
+ }
1621
+
1606
1622
for (unsigned candidateIdx :
1607
1623
indices (argumentCandidates[argIdx])) {
1608
1624
// If one of the candidates matched exactly there is no reason
0 commit comments