Type of expression is ambiguous without more context

I'm having problems with the following code. The particular function I'm having problems with is charCountRec. The error I'm getting is type of expression is ambiguous without more context.

func merging(_ dict1: [Character: Int], with dict2: [Character: Int]) -> [Character: Int] {
    var newDict : [Character: Int ] = [:]
    for (key,value) in dict1 {
        newDict[key] = value
    } 
    for (key,value) in dict2 {
        newDict[key] = value
    }
    return newDict
    
}

extension Dictionary {
    /// Creates a new dictionary from the key-value pairs in the given sequence.
    ///
    /// - Parameter keysAndValues: A sequence of key-value pairs to use for
    ///   the new dictionary. Every key in `keysAndValues` must be unique.
    /// - Returns: A new dictionary initialized with the elements of `keysAndValues`.
    /// - Precondition: The sequence must not have duplicate keys.
    /// - Note: Differs from the initializer in the standard library, which doesn't allow labeled tuple elements.
    ///     This can't support *all* labels, but it does support `(key:value:)` specifically,
    ///     which `Dictionary` and `KeyValuePairs` use for their elements.
    init<Elements: Sequence>(uniqueKeysWithValues keysAndValues: Elements)
    where Elements.Element == Element {
      self.init(
        uniqueKeysWithValues: keysAndValues.map { ($0.key, $0.value) }
      )
    }
  }

func charCountRec( str: String, result: inout [Character: Int]) -> [Character: Int] {
    var res : [Character: Int] = [:]
    var firstIndex = str.startIndex
    if str.count == 1 {
        res[str[firstIndex]] = 1
        return res
    } else if str.count > 1 {
        firstIndex = str.startIndex
        result[str[firstIndex]]! += 1
        var partialResult : [Character: Int] = [:]
        for _ in 1...result.count {
            result.dropLast()
        }
        partialResult = charCountRec(str: str, result: &Dictionary(result.dropFirst()))
        // Append the two dictionaries together
        return merging( result, with: partialResult)
    }
}

There are a couple inconsistencies in the charCountRec function. Below, I added "// <1>" and "// <2>" to refer to specific lines:

func charCountRec(str: String, result: inout [Character: Int]) -> [Character: Int] {
  var res: [Character: Int] = [:]
  var firstIndex = str.startIndex
  if str.count == 1 {
    res[str[firstIndex]] = 1
    return res
  } else if str.count > 1 {
    firstIndex = str.startIndex
    result[str[firstIndex]]! += 1
    var partialResult: [Character: Int] = [:]
    for _ in 1...result.count {
      _ = result.dropLast()
    }
    partialResult = charCountRec(str: str, result: &Dictionary(result.dropFirst())) // <1>
    // Append the two dictionaries together
    return merging(result, with: partialResult)
  }
  // <2>
}
  • at line <1> you're using Dictionary(result.dropFirst()), you're missing the uniqueKeysWithValues: label.
  • at line <1> you're passing the constant Dictionary(result.dropFirst()) as an inout parameter, but since it's a constant it cannot be mutated. You should declare it as a variable.
  • at line <2> you don't return, so your function returns a dictionary only when str.count is greater or equal to 1. You should return something also when str.count is 0.

The compiler should correctly show these 3 errors. Which version of Xcode are you using?