<p>You are given a string <code>s</code>.</p>

<p>You can perform the following process on <code>s</code> <strong>any</strong> number of times:</p>

<ul>
	<li>Choose an index <code>i</code> in the string such that there is <strong>at least</strong> one character to the left of index <code>i</code> that is equal to <code>s[i]</code>, and <strong>at least</strong> one character to the right that is also equal to <code>s[i]</code>.</li>
	<li>Delete the <strong>closest</strong> character to the <strong>left</strong> of index <code>i</code> that is equal to <code>s[i]</code>.</li>
	<li>Delete the <strong>closest</strong> character to the <strong>right</strong> of index <code>i</code> that is equal to <code>s[i]</code>.</li>
</ul>

<p>Return the <strong>minimum</strong> length of the final string <code>s</code> that you can achieve.</p>

<p>&nbsp;</p>
<p><strong class="example">Example 1:</strong></p>

<div class="example-block">
<p><strong>Input:</strong> <span class="example-io">s = &quot;abaacbcbb&quot;</span></p>

<p><strong>Output:</strong> <span class="example-io">5</span></p>

<p><strong>Explanation:</strong><br />
We do the following operations:</p>

<ul>
	<li>Choose index 2, then remove the characters at indices 0 and 3. The resulting string is <code>s = &quot;bacbcbb&quot;</code>.</li>
	<li>Choose index 3, then remove the characters at indices 0 and 5. The resulting string is <code>s = &quot;acbcb&quot;</code>.</li>
</ul>
</div>

<p><strong class="example">Example 2:</strong></p>

<div class="example-block">
<p><strong>Input:</strong> <span class="example-io">s = &quot;aa&quot;</span></p>

<p><strong>Output:</strong> <span class="example-io">2</span></p>

<p><strong>Explanation:</strong><br />
We cannot perform any operations, so we return the length of the original string.</p>
</div>

<p>&nbsp;</p>
<p><strong>Constraints:</strong></p>

<ul>
	<li><code>1 &lt;= s.length &lt;= 2 * 10<sup>5</sup></code></li>
	<li><code>s</code> consists only of lowercase English letters.</li>
</ul>

class Solution:
    def minimumLength(self, s: str) -> int:
        """
        exuastively performs all possible operations and return the min length of the string
        counting approach: 
        Time complexity: O(N)
        Space complexity: O(N)
        a a a a a regardless of its index position. -> 1 a
        a a a a a a -> 2 a(s)
        """
        # res = 0
        # hash_map = {} # count occurences of each unique char
        # for x in s:
        #     hash_map[x] = 1 if x not in hash_map.keys() else (hash_map[x] + 1)
        
        # # perform operations
        # # if odd -> 1
        # # if even -> 2
        # for val in hash_map.values():
        #     if val % 2 == 0: # even
        #         res += 2
        #     else:
        #         res += 1
        # return res

        """
        trimming operations by using stacks
        """
        hash_map = {}
        for idx, x in enumerate(s):
            if x not in hash_map.keys():
                hash_map[x] = [idx] # add a new stack if x not in hash_map
            else:
                if len(hash_map[x]) == 2:
                    hash_map[x].pop(0) # Remove bottom of stack
                else:
                    hash_map[x].append(idx)
        
        # reconstruct the string
        res = [" "] * len(s)
        for val_list in hash_map.values():
            for idx in val_list:
                res[idx] = s[idx]
        res = "".join(res)
        print(res.replace(" ", ""))
        return sum(len(x) for x in hash_map.values())

19900