728x90
반응형
  • TCP/UDP 차이점 중에 보안 관련된 이슈
    • TCP
      • 호스트 사이에 세션이 설정되는 연결 지향
      • 보내는 순서 유지
      • 데이터 중복, 손실 없음
      • 승인 및 순차적인 데이터 전송을 통해 신뢰성 보장
      • 패킷 흐름 제어
      • 1:1 통신만 지원
    • UDP
      • 호스트 사이에 세션이 설정되지 않은 비연결성
      • 보내는 순서 유지하지 않음
      • 데이터 중복, 손실 가능
      • 전송 승인이나 데이터 정렬 보장하지 않음
      • 흐름 제어 없음
      • 1:1, 1:N, M:N(다대다) 통신 지원
    • 보안상 차이점
      • UDP는 stateless로 Request없을 때 Reply 수신하지 않음
      • UDP는 인증이 없음
      • UDP는 암호화가 없음 (대칭키 사용)
      • UDP는 Spoofing 공격에 취약함
  • OSI 설명
    • 네트워크에서 통신이 일어나는 과정을 7단계로 나눈 것
      • 물리 계층 (L1, Physical Layer)
        • 이 계층에서 사용되는 통신 단위는 비트이며 컴퓨터의 랜카드가 전기 신호를 받아 신호가 강하면 1, 약하면 0을 반환
      • 데이터 링크 계층 (L2, Data Link Layer)
        • 이 계층에서는 MAC 주소를 통해 내 컴퓨터와 다른 사람의 컴퓨터와 통신함 데이터 단위는 프레임이다.
          • 프레임의 구성 : 목적지 MAC 주소 + 출발지 MAC 주소 + 네트워크 데이터(패킷) + 트레일러
          • MAC 주소 : 랜카드의 ID, MAC주소는 한 자리당 4bit씩 12자리로 구성
      • 네트워크 계층 (L3, Network Layer)
        • 데이터 링크 계층의 데이터가 네트워크 계층의 데이터이다. 이 계층에서 IP주소가 사용된다. 데이터 단위는 패킷이다.
          • 패킷의 구성 : 목적지 IP 주소 + 출발지 IP 주소 + 전송 계층 데이터 (세그먼트)
      • 전송 계층 (L4, Transport Layer)
        • 데이터 전송을 위해서 포트 번호를 사용함. 대표적인 프로토콜로 TCP, UDP가 있음. 포트를 통해 어떤 프로그램이 이 데이터를 처리해야 되는지 알 수 있다.
          • TCP : 3-way handshake를 통해 데이터를 받았는지 확인하고 연결 맺었는지 확인
          • UDP : 연결 맺고 난 후 별도의 확인작업 없이 데이터를 보냄
          • 세그먼트의 구성 : TCP 헤더 (목적지 Port 주소 + 출발지 Port 주소) + 세션 계층 데이터
          • 데이터 그램의 구성 : UDP 헤더 (목적지 Port 주소 + 출발지 Port 주소) + 데이터
      • 세션 계층 (L5, Session Layer)
        • 세션 계층은 TCP/IP 세션을 만들고 없애는 계층이다. 이를 통해 통신 장치 간 상호작용 및 동기화를 제공하고 연결 세션에서 데이터 교환과 에러 발생 시의 복구를 관리
      • 표현 계층 (L6, Presentation Layer)
        • 표현 계층은 데이터를 어떻게 표현할지 정하는 계층이다. 데이터의 형식상 차이를 다루는 부담을 응용 계층으로부터 덜어준다.
      • 응용 계층 (L7, Application Layer)
        • 사용자와 가장 밀접한 계층으로 인터페이스 역할을 하며 HTTP, FTP, SMTP, POP3, IMAP, Telnet등과 같은 프로토콜이 있다. 포트를 실제로 처리하는 계층은 여기서 이루어지고 응용 계층은 응용 프로세스와 직접 관계하여 일반적인 응용 서비스를 수행한다.
  • AES-256 암호화/복호화 이슈
    • AES-256은 대칭키 방식으로 암호화 및 복호화에 사용되는 키 값이 동일함
    • AES 128, AES 192, AES 256이 있는데 뒤에 숫자는 바이트를 의미하고 키 값이 길면 무작위 대입 공격에 유리하다는 자엄이 있다.
    • AES키를 하드 코딩하기보다는 키 값에 사용될 값을 숨겨야 한다 방법은 여러가지 인데
      • AOS는 Keystore를 사용해 키 저장, IOS는 Keychain을 사용해 키 저장, Unity IL2CPP로 빌드하여 추가 난독화를 적용
      • 클라우드 KMS를 사용하여 키를 클라우드에서 가져오고 앱 메모리에만 유지
      • 사용자의 로그인 정보를 기반으로 키를 생성하여 고유한 보안 계층을 추가한다.
  • map/set 자료구조
    • map
      • key/value 의 쌍으로 이루어진 트리임, 검색을 빠르게 하고 싶은 경우 사용하며 key를 기준으로 정렬된 상태여서 검색이 빠르다 (key값이 중복 되지 않는다)
    • set
      • key만 있는 map이라고 보면 된다, 정렬되어 있기 때문에 검색이 빠르다 (key 값이 중복 되지 않는다)
  • 에셋 번들 관리 및 만드는 법
    • C# 스크립트는 에셋 번들로 만들 수 없음 (비쥬얼 스크립트는 가능)
    • 에셋 번들 태그를 설정하고 동일한 태그를 가진 에셋들은 하나의 번들 파일로 패키징 된다.
    • 에셋 번들을 빌드하면 번들 파일 외에 Manifest 파일이 생성되어 에셋 번들 간의 의존성을 추적한다.
    • 에셋 번들 로드
      • 비동기 로드 또는 로컬/원격 로드가 있다
      • 비동기 로드 → 에셋 번들 로드할 때 메인 스레드를 차단하지 않고, 별도의 스레드에서 비동기로 작업을 수행한다. 즉, 작업이 완료될 때까지 앱이 멈추지 않고 계속 실행
        • 장점 : 로드 중에도 게임 정상 작동, 프레임 레이트 유지, 대규모 에셋을 로드할 때 성능 저하 방지
        • 단점 : 로드 완료 시점을 정확히 알기 위해서 코루틴 또는 콜백을 사용해야 함
      • 로컬 로드 → 에셋 번들을 로드할 때 디바이스의 로컬 스토리지에서 에셋 번들을 읽어오는 방식
        • 장점 : 네트워크 연결이 없어서 빠르고 안정적, 오프라인에서도 작동 가능
        • 단점 : 모든 에셋을 미리 포함해야 해서 앱 크기가 커질 수 있음, 콘텐츠 업데이트를 위해 전체 앱을 다시 배포해야 함
      • 원격 로드 → 에셋 번들을 원격 서버에서 다운하거나 스트리밍 방식으로 로드하는 방식 (UnityWebRequest 사용)
        • 장점 : 앱 설치 후에도 새 컨텐츠를 제공하거나 업데이트 가능, 초기 앱 크기를 줄일 수 있음
        • 단점 : 네트워크 연결 필요, 연결 상태가 나쁘면 속도가 느림, 서버 설정 및 관리를 추가적으로 해야함
    • 에셋 번들 관리
      • 의존 번들을 먼저 로드 (Manifest 파일 읽기) 해야 한다.
      • 서버에서 에셋 번들의 해시 또는 버전을 관리하여 클라이언트가 최신 번들을 로드하도록 구현해야하는데 Manifest의 해시 정보를 사용하여 UnityWebRequest를 사용해 필요한 번들만 다운로드한다.
  • 클라이언트에서 스테이지 데이터 받을 때 바뀐 스테이지는 어떻게 아는지
    • 각 스테이지 파일의 해시 값을 생성하여 관리
      • 로컬에 저장된 파일의 해시를 계산한 후 서버의 해시와 비교해서 다운
      • 장점 : 파일 내용이 변경 되면 정확하게 판단 가능, 이름이 같아도 내용이 다르면 탐지 가능
      • 단점 : 해시 값을 비교해야 해서 처리 시간 추가
    • 마지막 수정 시간 비교
      • 서버에서 스테이지 파일의 마지막 수정 시간을 가져와서 수정 시간이 로컬에 저장된 수정 시간과 다르면 다운
      • 장점 : 해시 계산보다 성능이 좋음, 간단하게 구현 가능
      • 단점 : 내용이 동일하지만 수정 시간이 달라질 경우, 불필요한 다운로드 발생
  • http 통신 과정
    • 요청 준비
      • 클라이언트에서 요청 준비 (URL 지정, HTTP 메소드 선택, 헤더와 데이터 설정)
    • 요청
      • 클라이언트에서 서버로 요청
    • 요청 처리
      • 서버는 요청 내용을 분석하고 필요한 데이터를 처리
    • 응답 반환
      • 클라이언트에게 요청 결과 반환
    • 응답 처리
      • 클라이언트는 응답 데이터를 사용해서 화면에 출력하거나 추가 작업을 수행
  • 옵저버 패턴이 정확하게 뭔지
    • 주체(Subject)에 관찰자(Observer)를 등록
    • 주체의 상태가 변경되면 등록된 모든 관찰자들에게 알림을 보냄
    • 관찰자들은 주체로부터 상태 정보를 가져와 각자의 방식으로 갱신하거나 작업 수행
728x90
반응형

'일상' 카테고리의 다른 글

지난 날의 내 Git 잔디  (0) 2024.01.09
728x90
반응형
  • 문제

준호는 요즘 디펜스 게임에 푹 빠져 있습니다. 디펜스 게임은 준호가 보유한 병사 n명으로 연속되는 적의 공격을 순서대로 막는 게임입니다. 디펜스 게임은 다음과 같은 규칙으로 진행됩니다.

  • 준호는 처음에 병사 n명을 가지고 있습니다.
  • 매 라운드마다 enemy[i]마리의 적이 등장합니다.
  • 병사 중 enemy[i]명 만큼 소모하여 enemy[i]마리의 적을 막을 수 있습니다.
    • 예를 들어 남은 병사가 7명이고, 적의 수가 2마리인 경우, 현재 라운드를 막으면 7 - 2 = 5명의 병사가 남습니다.
    • 남은 병사의 수보다 현재 라운드의 적의 수가 더 많으면 게임이 종료됩니다.
  • 게임에는 무적권이라는 스킬이 있으며, 무적권을 사용하면 병사의 소모없이 한 라운드의 공격을 막을 수 있습니다.
  • 무적권은 최대 k번 사용할 수 있습니다.
    준호는 무적권을 적절한 시기에 사용하여 최대한 많은 라운드를 진행하고 싶습니다.

준호가 처음 가지고 있는 병사의 수 n, 사용 가능한 무적권의 횟수 k, 매 라운드마다 공격해오는 적의 수가 순서대로 담긴 정수 배열 enemy가 매개변수로 주어집니다. 준호가 몇 라운드까지 막을 수 있는지 return 하도록 solution 함수를 완성해주세요.

  • 제한 사항

1 ≤ n ≤ 1,000,000,000
1 ≤ k ≤ 500,000
1 ≤ enemy의 길이 ≤ 1,000,000
1 ≤ enemy[i] ≤ 1,000,000
enemy[i]에는 i + 1 라운드에서 공격해오는 적의 수가 담겨있습니다.
모든 라운드를 막을 수 있는 경우에는 enemy[i]의 길이를 return 해주세요.

  • 입출력 예시
n k enemy result
7 3 [4, 2, 4, 5, 3, 3, 1] 5
2 4 [3, 3, 3, 3] 4
  • 접근방식

우선 순위 큐가 떠올랐다. 우선 순위 큐란 간단히 말해서 큐와 같이 선입 선출의 자료구조이지만 우선 순위가 높은 데이터가 먼저 나가는 자료구조로 힙을 기반으로 구현되어 있다.

1. 우선 순위 큐를 오름 차순으로 선언 (top에 가장 작은 값)

2. enemy의 크기만큼 반복하면서 우선 순위 큐에 현재 순번 enemy를 담고

3. k의 개수보다 많이 쌓이면 answer에 우선 순위 큐 top을 더하고 pop 해준다

4. answer이 n보다 커지면 i (라운드) 반환

5. 모든 라운드 통과면 enemy의 크기 반환

  • 코드
#include <vector>
#include <queue>

using namespace std;

int solution(int n, int k, vector<int> enemy)
{
    int answer = 0;
    
    priority_queue<int, vector<int>, greater<int>> pq;
    
    for (int i = 0; i < enemy.size(); i++)
    {
        pq.push(enemy[i]);
        
        if (pq.size() > k)
        {
            answer += pq.top();
            pq.pop();
        }
        
        if (answer > n)
        {
            return i;
        }
    }
    
    return enemy.size();
}

문제링크 :https://school.programmers.co.kr/learn/courses/30/lessons/142085

 

프로그래머스

SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프

programmers.co.kr

 

728x90
반응형
728x90
반응형
  • 문제

길이가 같은 배열 A, B 두개가 있습니다. 각 배열은 자연수로 이루어져 있습니다.
배열 A, B에서 각각 한 개의 숫자를 뽑아 두 수를 곱합니다. 이러한 과정을 배열의 길이만큼 반복하며, 두 수를 곱한 값을 누적하여 더합니다. 이때 최종적으로 누적된 값이 최소가 되도록 만드는 것이 목표입니다. (단, 각 배열에서 k번째 숫자를 뽑았다면 다음에 k번째 숫자는 다시 뽑을 수 없습니다.)

예를 들어 A = [1, 4, 2] , B = [5, 4, 4] 라면

  • A에서 첫번째 숫자인 1, B에서 첫번째 숫자인 5를 뽑아 곱하여 더합니다. (누적된 값 : 0 + 5(1x5) = 5)
  • A에서 두번째 숫자인 4, B에서 세번째 숫자인 4를 뽑아 곱하여 더합니다. (누적된 값 : 5 + 16(4x4) = 21)
  • A에서 세번째 숫자인 2, B에서 두번째 숫자인 4를 뽑아 곱하여 더합니다. (누적된 값 : 21 + 8(2x4) = 29)
    즉, 이 경우가 최소가 되므로 29를 return 합니다.

배열 A, B가 주어질 때 최종적으로 누적된 최솟값을 return 하는 solution 함수를 완성해 주세요.

  • 제한 사항

배열 A, B의 크기 : 1,000 이하의 자연수
배열 A, B의 원소의 크기 : 1,000 이하의 자연수

  • 입출력 예시
A B answer
[1, 4, 2] [5, 4, 4] 29
[1,2] [3,4] 10
  • 접근방식

1. A와 B의 두 수를 곱했을 때 가장 작은 값이 나와야 다 더했을 때 최솟값이 됨

2. A를 오름 차순 정렬, B를 내림 차순 정렬하고 곱하면 된다

  • 코드
#include <vector>
#include <algorithm>

using namespace std;

int solution(vector<int> A, vector<int> B)
{
    int answer = 0;

    sort(A.begin(), A.end());
    sort(B.rbegin(), B.rend());

    for (int i = 0; i < A.size(); i++)
    {
        answer += A[i] * B[i];
    }

    return answer;
}

문제링크 :https://school.programmers.co.kr/learn/courses/30/lessons/12941

 

프로그래머스

SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프

programmers.co.kr

 

728x90
반응형
728x90
반응형
  • 문제

위와 같은 삼각형의 꼭대기에서 바닥까지 이어지는 경로 중, 거쳐간 숫자의 합이 가장 큰 경우를 찾아보려고 합니다. 아래 칸으로 이동할 때는 대각선 방향으로 한 칸 오른쪽 또는 왼쪽으로만 이동 가능합니다. 예를 들어 3에서는 그 아래칸의 8 또는 1로만 이동이 가능합니다.

삼각형의 정보가 담긴 배열 triangle이 매개변수로 주어질 때, 거쳐간 숫자의 최댓값을 return 하도록 solution 함수를 완성하세요.

  • 제한 사항

삼각형의 높이는 1 이상 500 이하입니다.
삼각형을 이루고 있는 숫자는 0 이상 9,999 이하의 정수입니다.

  • 입출력 예시
triangle result
[[7], [3, 8], [8, 1, 0], [2, 7, 4, 4], [4, 5, 2, 6, 5]] 30
  • 접근방식
  1. 2차원 벡터 triangle을 표로 표현하면 아래와 같음
  j = 0 j = 1 j = 2 j = 3 j = 4
i = 0 7        
i = 1 3 8      
i = 2 8 1 0    
i = 3 2 7 4 4  
i = 4 4 5 2 6 5
    2. 표를 보면 i와 j의 위치를 가지고 본인 아래에 인접한 두 수를 찾을 수 있다. (왼쪽:i - 1, j) (오른쪽:i - 1, j - 1)
    3. 임의의 2차원 배열(또는 벡터) dp를 정의하고 dp[i][j] = max(dp[i - 1][j], dp[i - 1][j - 1]) + triangle[i][j] 인데
    4. 해당 행에서 숫자가 제일 왼쪽인 경우( j == 0)와 제일 오른쪽인 경우(j == i)만 예외 처리를 해주면 된다
    5. 반복문 끝에 dp[i][j] += triangle[i][j]를 해주어서 dp에 저장되어 있는 값 중 제일 큰 값으로 계산해도 되지만 answer과 dp[i][j]를 바로 비교해도 괜찮다
  • 코드
#include <string>
#include <vector>
#include <algorithm>

using namespace std;

int solution(vector<vector<int>> triangle)
{
    int answer = 0;
    
    vector<vector<int>> dp;
    dp.assign(501, vector<int>(501, 0));
    
    dp[0][0] = triangle[0][0];
    
    for (int i = 1; i < triangle.size(); i++)
    {
        for(int j = 0; j <= i; j++)
        {
            if (j == 0) // 제일 왼쪽
            {
                dp[i][j] = dp[i - 1][j] + triangle[i][j];
            }
            else if (j == i) // 제일 오른쪽
            {
                dp[i][j] = dp[i - 1][j - 1] + triangle[i][j];
            }
            else
            {
                dp[i][j] = max(dp[i - 1][j - 1], dp[i - 1][j]) + triangle[i][j];
            }
            
            answer = max(answer, dp[i][j]);
        }
    }
    
    
    return answer;
}

문제링크 : https://school.programmers.co.kr/learn/courses/30/lessons/43105

 

프로그래머스

SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프

programmers.co.kr

728x90
반응형
728x90
반응형
  • 문제

xx 회사의 2xN명의 사원들은 N명씩 두 팀으로 나눠 숫자 게임을 하려고 합니다. 두 개의 팀을 각각 A팀과 B팀이라고 하겠습니다. 숫자 게임의 규칙은 다음과 같습니다.

  • 먼저 모든 사원이 무작위로 자연수를 하나씩 부여받습니다.
  • 사원은 딱 한 번씩 경기를 합니다.
  • 각 경기당 A팀에서 한 사원이, B팀에서 한 사원이 나와 서로의 수를 공개합니다. 그때 숫자가 큰 쪽이 승리하게 되고, 승리한 사원이 속한 팀은 승점을 1점 얻게 됩니다.
  • 만약 숫자가 같다면 누구도 승점을 얻지 않습니다.

전체 사원들은 우선 무작위로 자연수를 하나씩 부여받았습니다. 그다음 A팀은 빠르게 출전순서를 정했고 자신들의 출전 순서를 B팀에게 공개해버렸습니다. B팀은 그것을 보고 자신들의 최종 승점을 가장 높이는 방법으로 팀원들의 출전 순서를 정했습니다. 이때의 B팀이 얻는 승점을 구해주세요.
A 팀원들이 부여받은 수가 출전 순서대로 나열되어있는 배열 A와 i번째 원소가 B팀의 i번 팀원이 부여받은 수를 의미하는 배열 B가 주어질 때, B 팀원들이 얻을 수 있는 최대 승점을 return 하도록 solution 함수를 완성해주세요.

  • 제한 사항

A와 B의 길이는 같습니다.
A와 B의 길이는 1 이상 100,000 이하입니다.
A와 B의 각 원소는 1 이상 1,000,000,000 이하의 자연수입니다.

  • 입출력 예시
A B result
[5,1,3,7] [2,2,6,8] 3
[2,2,2,2] [1,1,1,1] 0
  • 접근방식
  1. 우선 두 벡터를 오름 차순으로 정렬 해보기
  2. aIndex와 bIndex를 0부터 시작해서 각각(aIndex, bIndex) 현재 A팀과 B팀의 크기보다 커지면 반복을 종료하는 반복문 시작
  3. B팀의 현재 숫자가 A팀의 숫자보다 큰 경우, 승점 획득 > A팀과 B팀 모두 다음으로 넘어감 (A팀 index++, B팀 index++)
  4. B팀의 현재 숫자가 A티므이 숫자보다 작은 경우, 해당 숫자 소모하고 B팀만 다음으로 넘어감 (B팀 index++)
  • 코드
#include <string>
#include <vector>
#include <algorithm>

using namespace std;

int solution(vector<int> A, vector<int> B)
{
    int answer = 0;
    
    sort(A.begin(), A.end());
    sort(B.begin(), B.end());
    
    int aIndex = 0;
    int bIndex = 0;
    
    while (aIndex < A.size() && bIndex < B.size())
    {
        if (A[aIndex] < B[bIndex])
        {
            answer++;
            aIndex++;
        }
        bIndex++;
    }
    
    return answer;
}

문제링크 : https://school.programmers.co.kr/learn/courses/30/lessons/12987

 

프로그래머스

SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프

programmers.co.kr

 

728x90
반응형
728x90
반응형
  • 문제

자연수 n 개로 이루어진 중복 집합(multi set, 편의상 이후에는 "집합"으로 통칭) 중에 다음 두 조건을 만족하는 집합을 최고의 집합이라고 합니다.

1. 각 원소의 합이 S가 되는 수의 집합
2. 위 조건을 만족하면서 각 원소의 곱 이 최대가 되는 집합
예를 들어서 자연수 2개로 이루어진 집합 중 합이 9가 되는 집합은 다음과 같이 4개가 있습니다.
{ 1, 8 }, { 2, 7 }, { 3, 6 }, { 4, 5 }
그중 각 원소의 곱이 최대인 { 4, 5 }가 최고의 집합입니다.

집합의 원소의 개수 n과 모든 원소들의 합 s가 매개변수로 주어질 때, 최고의 집합을 return 하는 solution 함수를 완성해주세요.

  • 제한 사항

최고의 집합은 오름차순으로 정렬된 1차원 배열(list, vector) 로 return 해주세요.
만약 최고의 집합이 존재하지 않는 경우에 크기가 1인 1차원 배열(list, vector) 에 -1 을 채워서 return 해주세요.
자연수의 개수 n은 1 이상 10,000 이하의 자연수입니다.
모든 원소들의 합 s는 1 이상, 100,000,000 이하의 자연수입니다.

  • 입출력 예시
n s result
2 9 [4, 5]
2 1 [-1]
2 8 [4, 4]
  • 접근방식
  1. 각 원소의 합이 s, 즉 겹치지 않는 원소의 곱이 최대가 되는 집합을 찾으면 됨
  2. 해당 집합은 n와 s를 나누기와 모듈러 연산을 통하여 구한다
  3. s / n 으로 나눈 해당 숫자를 n개 만큼 생성후
  4. s % n 으로 나운 숫자를 각각에 더해준다
  5. 단, 만들 수 없는 경우는 (n > s) -1만 담고 return
  • 코드
#include <string>
#include <vector>
#include <algorithm>

using namespace std;

vector<int> solution(int n, int s)
{
    vector<int> answer;
    
    if (n > s)
    {
        answer.push_back(-1);
        return answer;
    }
    
    int divideNumber = s / n;
    
    answer.assign(n, divideNumber);
    
    int modulerNumber = s % n;
    
    for (int i = 0; i < answer.size() && modulerNumber > 0; i++)
    {
        answer[i]++;
        modulerNumber--;
    }
    
    sort(answer.begin(), answer.end());
    return answer;
}

문제링크 : https://school.programmers.co.kr/learn/courses/30/lessons/12938

 

프로그래머스

SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프

programmers.co.kr

 

728x90
반응형
728x90
반응형
  • 문제

괄호가 바르게 짝지어졌다는 것은 '(' 문자로 열렸으면 반드시 짝지어서 ')' 문자로 닫혀야 한다는 뜻입니다. 예를 들어
"()()" 또는 "(())()" 는 올바른 괄호입니다.
")()(" 또는 "(()(" 는 올바르지 않은 괄호입니다.
'(' 또는 ')' 로만 이루어진 문자열 s가 주어졌을 때, 문자열 s가 올바른 괄호이면 true를 return 하고, 올바르지 않은 괄호이면 false를 return 하는 solution 함수를 완성해 주세요.

  • 제한 사항

문자열 s의 길이 : 100,000 이하의 자연수
문자열 s는 '(' 또는 ')' 로만 이루어져 있습니다.

  • 입출력 예시
s answer
"()()" true
"(())()" true
")()(" false
"(()(" false
  • 접근방식
  1. s에서 '('가 나오면 스택에 push
  2. 만약 다른 문자 ( ')' )가 나오고 스택에 요소가 존재하면 pop
  3. 그 외의 것은 false 출력
  4. 반복문이 끝난 후 스택이 남아 있지 않으면 true 출력
  • 코드
#include <string>
#include <iostream>
#include <stack>

using namespace std;

bool solution(string s)
{
    bool answer = false;
    stack<char> stk;
    for (int i = 0; i < s.length(); i++)
    {
        if (s[i] == '(')
        {
            stk.push(s[i]);
        }
        else if (stk.size())
        {
            stk.pop();
        }
        else
        {
            return answer;
        }
    }

    if (!stk.size())
    {
        answer = true;
    }

    
    return answer;
}

문제링크 : https://school.programmers.co.kr/learn/courses/30/lessons/12909

 

프로그래머스

SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프

programmers.co.kr

 

728x90
반응형
728x90
반응형
  • 문제

회사원 Demi는 가끔은 야근을 하는데요, 야근을 하면 야근 피로도가 쌓입니다. 야근 피로도는 야근을 시작한 시점에서 남은 일의 작업량을 제곱하여 더한 값입니다. Demi는 N시간 동안 야근 피로도를 최소화하도록 일할 겁니다.Demi가 1시간 동안 작업량 1만큼을 처리할 수 있다고 할 때, 퇴근까지 남은 N 시간과 각 일에 대한 작업량 works에 대해 야근 피로도를 최소화한 값을 리턴하는 함수 solution을 완성해주세요.

  • 제한 사항
    • works는 길이 1 이상, 20,000 이하인 배열입니다.
    • works의 원소는 50000 이하인 자연수입니다.
    • n은 1,000,000 이하인 자연수입니다
  • 입출력 예시
works n result
[4, 3, 3] 4 12
[2, 1, 2] 1 6
[1,1] 3 0
  • 접근방식

n만큼 반복 하면서 벡터를 내림 차순으로 정렬 후 가장 높은 수 만큼 빼는 것으로 접근

1. n이 0이 될 때 까지 반복하다가 n이 0이 되거나 내림 차순으로 정렬한 벡터의 맨 앞(Max 값)이 0이면 반복 종료

2. works에서 front를 미리 뽑아 놓고 works의 벡터를 순회해서 미리 뽑아 놓은 front와 해당 순차의 works값이 같으면 n값과 함께 빼주기

3. 그렇지 않고 works의 다음 값이 있으면 다시 내림 차순 정렬, 해당 반복문 종료

4.  works에 남아 있는 값 제곱해서 answer에 더해주기

  • 코드
#include <vector>
#include <algorithm>
#include <cmath>

using namespace std;

long long solution(int n, vector<int> works)
{
    long long answer = 0;
    
    sort(works.rbegin(), works.rend());

    while(n)
    {
        if (!works.front())
        {
            break;
        }
        
        int front = works.front();
        
        for (int i = 0; i < works.size(); i++)
        {
            if (!n)
            {
                break;
            }
            
            if (front == works[i])
            {
                works[i]--;
                n--;
            }
            else
            {
                if (i != works.size() - 1)
                {
                    if (works[i] < works[i + 1])
                    {
                        sort(works.rbegin(), works.rend());
                    }
                    break;
                }
            }
        }
    }
    
    for (int i = 0; i < works.size(); i++)
    {        
        answer += pow(works[i], 2);
    }
    
    return answer;
}
 

프로그래머스

SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프

programmers.co.kr

 

728x90
반응형

+ Recent posts