Check if a Parentheses String Can Be Valid

medium stack greedy parentheses

Problem

You are given a parentheses string s and a binary string locked of the same length. Wherever locked[i] is '1' the character s[i] is frozen in place; wherever it is '0' you may flip s[i] to either '(' or ')'.

Decide whether some choice for the free positions turns s into a valid parentheses string — one where every prefix has at least as many '(' as ')' and the totals match.

Inputs = "))()))", locked = "010100"
Outputtrue
Positions 1 and 3 hold locked ')', but flipping the free s[0] and s[4] to '(' gives "()()()".

def can_be_valid(s, locked):
    if len(s) % 2 == 1:
        return False
    bal = 0                       # forward: too many locked ')'?
    for i in range(len(s)):
        if locked[i] == '0' or s[i] == '(':
            bal += 1
        else:
            bal -= 1
        if bal < 0:
            return False
    bal = 0                       # backward: too many locked '('?
    for i in range(len(s) - 1, -1, -1):
        if locked[i] == '0' or s[i] == ')':
            bal += 1
        else:
            bal -= 1
        if bal < 0:
            return False
    return True
function canBeValid(s, locked) {
  if (s.length % 2 === 1) return false;
  let bal = 0;                    // forward: too many locked ')'?
  for (let i = 0; i < s.length; i++) {
    if (locked[i] === '0' || s[i] === '(') bal++;
    else bal--;
    if (bal < 0) return false;
  }
  bal = 0;                        // backward: too many locked '('?
  for (let i = s.length - 1; i >= 0; i--) {
    if (locked[i] === '0' || s[i] === ')') bal++;
    else bal--;
    if (bal < 0) return false;
  }
  return true;
}
boolean canBeValid(String s, String locked) {
    if (s.length() % 2 == 1) return false;
    int bal = 0;                  // forward: too many locked ')'?
    for (int i = 0; i < s.length(); i++) {
        if (locked.charAt(i) == '0' || s.charAt(i) == '(') bal++;
        else bal--;
        if (bal < 0) return false;
    }
    bal = 0;                      // backward: too many locked '('?
    for (int i = s.length() - 1; i >= 0; i--) {
        if (locked.charAt(i) == '0' || s.charAt(i) == ')') bal++;
        else bal--;
        if (bal < 0) return false;
    }
    return true;
}
bool canBeValid(string s, string locked) {
    if (s.size() % 2 == 1) return false;
    int bal = 0;                  // forward: too many locked ')'?
    for (int i = 0; i < (int)s.size(); i++) {
        if (locked[i] == '0' || s[i] == '(') bal++;
        else bal--;
        if (bal < 0) return false;
    }
    bal = 0;                      // backward: too many locked '('?
    for (int i = (int)s.size() - 1; i >= 0; i--) {
        if (locked[i] == '0' || s[i] == ')') bal++;
        else bal--;
        if (bal < 0) return false;
    }
    return true;
}
Time: O(n) Space: O(1)