def check(input_string):
stack = []
brackets = { '{': '}', '(': ')', '[': ']' }
brackets_rev = {v: k for k, v in brackets.items()}
for idx, ch in enumerate(input_string):
if ch in brackets:
stack.append(ch)
elif ch in brackets_rev:
if not stack:
return False, 'Closing parenthesis without open one at {0}'.format(idx)
if stack.pop(-1) != brackets_rev[ch]:
return False, 'Invalid bracket at idx {0}: "{1}" (expected "{2}")'.format(idx, ch, brackets_rev[ch])
if stack:
return False, 'Unbalanced: {0}'.format(', '.join(stack))
return True, None
print(check("()"))
print(check("[{}]()"))
print(check("({)[}]"))
ZGVmIGNoZWNrKGlucHV0X3N0cmluZyk6CglzdGFjayA9IFtdCglicmFja2V0cyAgICAgPSB7ICd7JzogJ30nLCAnKCc6ICcpJywgJ1snOiAnXScgfQoJYnJhY2tldHNfcmV2ID0ge3Y6IGsgZm9yIGssIHYgaW4gYnJhY2tldHMuaXRlbXMoKX0KCWZvciBpZHgsIGNoIGluIGVudW1lcmF0ZShpbnB1dF9zdHJpbmcpOgoJCWlmIGNoIGluIGJyYWNrZXRzOgoJCQlzdGFjay5hcHBlbmQoY2gpCgkJZWxpZiBjaCBpbiBicmFja2V0c19yZXY6CgkJCWlmIG5vdCBzdGFjazoKCQkJCXJldHVybiBGYWxzZSwgJ0Nsb3NpbmcgcGFyZW50aGVzaXMgd2l0aG91dCBvcGVuIG9uZSBhdCB7MH0nLmZvcm1hdChpZHgpCgkJCQoJCQlpZiBzdGFjay5wb3AoLTEpICE9IGJyYWNrZXRzX3JldltjaF06CgkJCQlyZXR1cm4gRmFsc2UsICdJbnZhbGlkIGJyYWNrZXQgYXQgaWR4IHswfTogInsxfSIgKGV4cGVjdGVkICJ7Mn0iKScuZm9ybWF0KGlkeCwgY2gsIGJyYWNrZXRzX3JldltjaF0pCgkKCWlmIHN0YWNrOgoJCXJldHVybiBGYWxzZSwgJ1VuYmFsYW5jZWQ6IHswfScuZm9ybWF0KCcsICcuam9pbihzdGFjaykpCglyZXR1cm4gVHJ1ZSwgTm9uZQoKcHJpbnQoY2hlY2soIigpIikpCnByaW50KGNoZWNrKCJbe31dKCkiKSkKcHJpbnQoY2hlY2soIih7KVt9XSIpKQ==