title: Why does struct need to conform to Hashable as well as Generic array when converting to a dictionary
body: <p>The goal was to convert items in a generic list into a dictionary for the variable <code>uniqueKeys</code>, but I saw the error:</p>
  
  <blockquote>
    <p>Cannot subscript a value of incorrect or ambiguous type</p>
  </blockquote>
  
  <p>I knew something needed to conform to the <code>Hashable</code> protocol and eventually landed on the solution, but I don't completely understand why this solution works.</p>
  
  <ol>
  <li>I understand why <code>T</code> needs to be <code>Hashable</code> since its' going into a dictionary key, but why also <code>CustomSet</code>?  </li>
  <li>If <code>CustomSet</code> uses <code>Hashable</code> why don't I need to write anything in its extension?</li>
  </ol>
  
  <p><strong>initial code</strong></p>
  
  <pre><code>struct CustomSet&lt;T : Comparable &gt; {
      private var list: [T]
      init(_ list: [T]){
          let uniqueKeys = list.reduce(into: [:]){ dict, item in
              dict[item, default: 0] += 1
          }.keys
          self.list = Array(uniqueKeys)
      }
  }
  
  extension CustomSet : Equatable {
      static func == (lhs: CustomSet, rhs: CustomSet) -&gt; Bool {
          return lhs.list.count == rhs.list.count &amp;&amp; lhs.list.sorted() == rhs.list.sorted()
      }
  }  
  </code></pre>
  
  <p><strong>I finally resolved it with:</strong></p>
  
  <pre><code>struct CustomSet&lt;T : Comparable &gt; : Hashable where T : Hashable {
      private var list: [T]
      init(_ list: [T]){
          let uniqueKeys = list.reduce(into: [:]){ dict, item in
              dict[item, default: 0] += 1
          }.keys
          self.list = Array(uniqueKeys)
      }
  }
  
  extension CustomSet : Equatable {
      static func == (lhs: CustomSet, rhs: CustomSet) -&gt; Bool {
          return lhs.list.count == rhs.list.count &amp;&amp; lhs.list.sorted() == rhs.list.sorted()
      }
  }  
  </code></pre>
  
  <p>I also noticed that factoring into an extension: <code>extension CustomSet: Hashable where T : Hashable</code> doesn't seem to be the same as <code>struct CustomSet&lt;T : Comparable &gt; : Hashable where T : Hashable</code> in terms of adding the Hashable protocol because I still see that error</p>
  
  <p><strong>What I tried</strong>  </p>
  
  <p>If I add this to the generic type <code>T</code> I still saw the same error.</p>
  
  <pre><code>struct CustomSet&lt;T : Comparable, Hashable &gt;
  </code></pre>
  
  <p>If I add <code>Hashable</code> to <code>CustomSet</code> I see the error </p>
  
  <blockquote>
    <p>Cannot convert value of type '[T]' to expected argument type
    'UnsafeRawBufferPointer'</p>
  </blockquote>
  
  <p>and</p>
  
  <blockquote>
    <p>Inheritance from non-protocol type 'Hashable'</p>
  </blockquote>
  
  <pre><code>extension CustomSet : Equatable, Hashable {
      static func == (lhs: CustomSet, rhs: CustomSet) -&gt; Bool {
          return lhs.list.count == rhs.list.count &amp;&amp; lhs.list.sorted() == rhs.list.sorted()
      }
  
      func hash(into hasher: inout Hasher) {
         var hashValue: Int {
             var hasher = Hasher()
             self.hash(into: &amp;hasher)
             return hasher.finalize()
         }
      }
   }
  </code></pre>