{ }codelper
스택참·거짓 함수P0040

괄호 짝 맞추기

괄호 글자 ( ) [ ] { } 로만 이루어진 문자열이 한 줄 주어진다.
모든 여는 괄호가 같은 종류의 닫는 괄호와 올바른 차례로 짝지어지면 "예", 아니면 "아니요"를 출력하라.
올바른 차례란, 닫는 괄호가 나올 때마다 아직 닫히지 않은 여는 괄호 가운데 가장 나중에 열린 것과 종류가 같아야 한다는 뜻이다.
예를 들어 "{[()]}"와 "()[]"는 yes, "([)]"·"(("·")("는 no이다.

입력
문자열 길이 1 이상 10,000 이하.
( ) [ ] { } 밖의 글자나 빈칸은 없다.
출력
yes 또는 no
예시 1 · stdin
{[()()]}
stdout
예
예시 2 · stdin
([)]
stdout
아니요
main.py
입력(stdin)

실행하면 이 줄들이 차례로 input()·표준 입력으로 들어가요(실행 중에 묻지 않아요).

$ 준비됐어요

코드를 입력해 풀려면 PC에서 열어 주세요. 모바일에서는 문제와 풀이를 볼 수 있어요.

다른 언어로는?언어별 풀이 보기 · 8개 언어 풀이

여는 괄호는 쌓고, 닫는 괄호가 오면 맨 위를 꺼내 종류를 비교하는 스택 문제예요.
함정 세 가지: 종류별 개수만 세면 "([)]"를 못 잡고, 닫는 괄호가 왔을 때 스택이 비었는지 안 보면 ")"에서 Python pop()은 IndexError, C++ std::stack::top()은 정의되지 않은 동작이 되며, 끝에 스택이 비었는지 안 보면 "((("가 yes가 돼요.
스택 도구: Python list의 append/pop, JavaScript·TypeScript 배열의 push/pop, Java ArrayDeque(옛 Stack 클래스보다 권장), C# Stack<char>, C++ std::stack(top()으로 보고 pop()으로 버리는 두 단계), C는 배열과 맨 위 번호 하나.
크레이콘은 목록으로 stack.넣기(c), 맨 위는 stack[stack.개수 - 1], 꺼내기는 stack.자리빼기(stack.개수 - 1)이고, 목록에 10,000개까지만 넣을 수 있어 길이 제한을 10,000으로 맞췄어요.

Pythonmain.py · 12 줄
def is_balanced(s):    match = {")": "(", "]": "[", "}": "{"}    stack = []    for c in s:        if c in "([{":            stack.append(c)        elif not stack or stack.pop() != match[c]:            return False    return not stack  print("예" if is_balanced(input().strip()) else "아니요")
JavaScriptmain.js · 13 줄
const s = require("fs").readFileSync(0, "utf8").trim(); function isBalanced(s) {  const match = { ")": "(", "]": "[", "}": "{" };  const stack = [];  for (const c of s) {    if ("([{".includes(c)) stack.push(c);    else if (stack.length === 0 || stack.pop() !== match[c]) return false;  }  return stack.length === 0;} console.log(isBalanced(s) ? "예" : "아니요");
TypeScriptmain.ts · 14 줄
import { readFileSync } from "node:fs";const s: string = readFileSync(0, "utf8").trim(); function isBalanced(s: string): boolean {  const match: Record<string, string> = { ")": "(", "]": "[", "}": "{" };  const stack: string[] = [];  for (const c of s) {    if ("([{".includes(c)) stack.push(c);    else if (stack.length === 0 || stack.pop() !== match[c]) return false;  }  return stack.length === 0;} console.log(isBalanced(s) ? "예" : "아니요");
JavaMain.java · 25 줄
import java.io.BufferedReader;import java.io.IOException;import java.io.InputStreamReader;import java.util.ArrayDeque;import java.util.Deque; public class Main {    static boolean isBalanced(String s) {        Deque<Character> stack = new ArrayDeque<>();        for (char c : s.toCharArray()) {            if (c == '(' || c == '[' || c == '{') {                stack.push(c);            } else {                char open = c == ')' ? '(' : c == ']' ? '[' : '{';                if (stack.isEmpty() || stack.pop() != open) return false;            }        }        return stack.isEmpty();    }     public static void main(String[] args) throws IOException {        String s = new BufferedReader(new InputStreamReader(System.in)).readLine().trim();        System.out.println(isBalanced(s) ? "예" : "아니요");    }}
C#Main.cs · 29 줄
using System;using System.Collections.Generic; class Program{    static bool IsBalanced(string s)    {        var stack = new Stack<char>();        foreach (char c in s)        {            if (c == '(' || c == '[' || c == '{')            {                stack.Push(c);            }            else            {                char open = c == ')' ? '(' : c == ']' ? '[' : '{';                if (stack.Count == 0 || stack.Pop() != open) return false;            }        }        return stack.Count == 0;    }     static void Main()    {        string s = Console.ReadLine().Trim();        Console.WriteLine(IsBalanced(s) ? "예" : "아니요");    }}
C++main.cpp · 23 줄
#include <iostream>#include <stack>#include <string> bool isBalanced(const std::string& s) {    std::stack<char> st;    for (char c : s) {        if (c == '(' || c == '[' || c == '{') {            st.push(c);        } else {            char open = c == ')' ? '(' : c == ']' ? '[' : '{';            if (st.empty() || st.top() != open) return false;            st.pop();        }    }    return st.empty();} int main() {    std::string s;    std::cin >> s;    std::cout << (isBalanced(s) ? "예" : "아니요") << '\n';}
Cmain.c · 24 줄
#include <stdbool.h>#include <stdio.h> static char s[10001], stack[10000]; bool is_balanced(const char *s) {    int top = 0;    for (int i = 0; s[i]; i++) {        char c = s[i];        if (c == '(' || c == '[' || c == '{') {            stack[top++] = c;        } else {            char open = c == ')' ? '(' : c == ']' ? '[' : '{';            if (top == 0 || stack[--top] != open) return false;        }    }    return top == 0;} int main(void) {    scanf("%10000s", s);    puts(is_balanced(s) ? "예" : "아니요");    return 0;}
Craykonmain.cray · 28 줄
짝맞나(s){    stack = [];    각각 (c 에서 s)    {        만약 (c == "(" || c == "[" || c == "{")        {            stack.넣기(c);        }        아니면        {            만약 (stack.개수 == 0)            {                돌려주기 거짓;            }            top = stack[stack.개수 - 1];            stack.자리빼기(stack.개수 - 1);            만약 (c == ")" && top != "(" || c == "]" && top != "[" || c == "}" && top != "{")            {                돌려주기 거짓;            }        }    }    돌려주기 stack.개수 == 0;} s = 콘솔.줄읽기().공백제거();콘솔.쓰기(짝맞나(s) ? "예" : "아니요");