<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
  <channel>
    <title>실험의 연속</title>
    <link>https://elastinn.tistory.com/</link>
    <description></description>
    <language>ko</language>
    <pubDate>Fri, 24 Jul 2026 03:44:54 +0900</pubDate>
    <generator>TISTORY</generator>
    <ttl>100</ttl>
    <managingEditor>탄력이</managingEditor>
    <item>
      <title>React useSWR 에서 mutate란 무엇인가? (useSWR의 mutate로 리액트 상태 관리 최적화하기)</title>
      <link>https://elastinn.tistory.com/13</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style3&quot;&gt;React 로 웹개발을 한다구요? &lt;span style=&quot;color: #000000;&quot;&gt;&lt;b&gt;댓글 create 구현을 했는데&lt;/b&gt;&lt;/span&gt; 페이지는 방금 만든 댓글을 가져오지 않아 &lt;span style=&quot;color: #000000;&quot;&gt;&lt;b&gt;새로 고침을 해야만 새로운 데이터가 그려진다구요???&lt;/b&gt;&lt;/span&gt;&lt;br /&gt;그렇다면 React &lt;span style=&quot;color: #000000;&quot;&gt;&lt;b&gt;useSWR 의 mutate 를 쓰는 방법을 알아봅시다.&lt;/b&gt;&lt;/span&gt;&lt;/blockquote&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;React 애플리케이션을 개발할 때, &lt;b&gt;데이터 페칭과 상태 관리&lt;/b&gt;는 &lt;b&gt;성능과 사용자 경험을 최적화&lt;/b&gt;하는 데 매우 중요합니다. 그렇기에 &lt;b&gt;SWR&lt;/b&gt;은 React 개발자들 사이에서 현재도 필수 도구로 자리 잡고 있습니다. 이 글에서는 SWR에서 제공하는 &lt;code&gt;mutate&lt;/code&gt; 함수가 무엇인지, 그리고 이 함수가 리액트 상태 관리에서 어떻게 최적화에 기여할 수 있는지에 대해 다루겠습니다.&lt;/p&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;SWR과 데이터 페칭의 중요성&lt;/h2&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;SWR&lt;/b&gt;은 &lt;b&gt;Stale-While-Revalidate&lt;/b&gt;의 약자로, &lt;b&gt;데이터를 가져오고 캐시하는 패턴을 구현&lt;/b&gt;하는 데 도움을 주는 라이브러리입니다. 이는 주로 &lt;b&gt;Next.js&lt;/b&gt; 또는 &lt;b&gt;React&lt;/b&gt; 프로젝트에서 서버로부터 데이터를 효율적으로 가져오고 관리하는 데 사용됩니다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;SWR의 가장 큰 장점은 &lt;b&gt;자동 캐싱&lt;/b&gt;과 &lt;b&gt;재검증(revalidation)&lt;/b&gt; 기능입니다. 이를 통해 서버와의 불필요한 요청을 줄이고, UI가 최신 상태를 유지할 수 있습니다. 하지만, 가끔 서버 응답을 기다리지 않고도 클라이언트 상태를 빠르게 업데이트해야 할 경우가 있는데, 바로 이때 &lt;b&gt;&lt;code&gt;mutate&lt;/code&gt;&lt;/b&gt;가 큰 역할을 합니다.&lt;/p&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;mutate란 무엇인가?&lt;/h2&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;SWR의 &lt;code&gt;mutate&lt;/code&gt;는 &lt;b&gt;SWR 캐시에 있는 데이터를 수동으로 업데이트&lt;/b&gt;하는 함수입니다. 즉, 서버로부터 다시 데이터를 가져오지 않고도 캐시에 있는 데이터를 변경할 수 있게 해줍니다. 이 기능을 사용하면 서버의 응답을 기다리지 않고도 UI를 빠르게 업데이트할 수 있으며, 이후 서버의 실제 데이터를 받아와 자동으로 캐시와 동기화할 수 있습니다.&lt;/p&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;&lt;code&gt;mutate&lt;/code&gt; 함수의 시그니처&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;code&gt;mutate&lt;/code&gt;는 SWR 훅을 사용하면 반환되는 함수 중 하나입니다. 다음은 &lt;code&gt;mutate&lt;/code&gt;의 기본 시그니처입니다:&lt;/p&gt;
&lt;pre class=&quot;haskell&quot;&gt;&lt;code&gt;mutate(key, data?, shouldRevalidate = true);&lt;/code&gt;&lt;/pre&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&lt;b&gt;&lt;code&gt;key&lt;/code&gt;&lt;/b&gt;: SWR의 캐시를 식별하는 고유 키입니다. 일반적으로 페칭하고자 하는 API URL을 사용합니다.&lt;/li&gt;
&lt;li&gt;&lt;b&gt;&lt;code&gt;data&lt;/code&gt;&lt;/b&gt;: SWR 캐시에 업데이트할 새로운 데이터입니다. 이 매개변수를 생략하면, SWR이 자동으로 서버로부터 데이터를 다시 가져와 업데이트합니다.&lt;/li&gt;
&lt;li&gt;&lt;b&gt;&lt;code&gt;shouldRevalidate&lt;/code&gt;&lt;/b&gt;: 기본값이 &lt;code&gt;true&lt;/code&gt;로 설정되어 있으며, 이 값이 &lt;code&gt;true&lt;/code&gt;일 경우 서버로부터 최신 데이터를 다시 가져옵니다. &lt;code&gt;false&lt;/code&gt;로 설정하면 주어진 데이터만 SWR 캐시에 반영하고, 서버 요청은 생략됩니다.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;mutate의 사용 시나리오&lt;/h2&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;1. &lt;b&gt;낙관적 업데이트 (Optimistic Update)&lt;/b&gt;&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;낙관적 업데이트는 서버 응답을 기다리지 않고 UI를 먼저 업데이트한 뒤, 서버 응답을 받아 상태를 동기화하는 방식입니다. 이 방식은 사용자 경험을 크게 향상시킵니다. 예를 들어, 댓글을 작성했을 때 서버 응답을 기다리지 않고 바로 UI에 반영하는 경우에 사용됩니다.&lt;/p&gt;
&lt;pre class=&quot;javascript&quot;&gt;&lt;code&gt;const { data: comments, mutate } = useSWR(`/posts/${postId}/comments`);

const addComment = async (newComment) =&amp;gt; {
  // 캐시된 데이터를 먼저 업데이트 (낙관적 업데이트)
  mutate([...comments, newComment], false);

  // 서버에 실제로 댓글을 추가하는 요청
  await fetch(`/api/comments`, {
    method: 'POST',
    body: JSON.stringify(newComment),
  });

  // 서버에서 최신 데이터 다시 받아오기
  mutate();
};&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 예시에서, &lt;code&gt;mutate([...comments, newComment], false)&lt;/code&gt;는 서버 응답 없이 로컬 상태를 즉시 업데이트하여 댓글을 추가하는 것처럼 보이게 합니다. 서버 요청이 완료된 후에 다시 &lt;code&gt;mutate()&lt;/code&gt;를 호출하여 최신 데이터를 가져옵니다.&lt;/p&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;2. &lt;b&gt;캐시 강제 업데이트&lt;/b&gt;&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;때로는 서버에서 데이터를 강제로 다시 가져와야 할 때가 있습니다. 예를 들어, 어떤 데이터를 수동으로 변경하고 나서 이를 최신 상태로 동기화할 때 &lt;code&gt;mutate()&lt;/code&gt;를 사용할 수 있습니다.&lt;/p&gt;
&lt;pre class=&quot;javascript&quot;&gt;&lt;code&gt;const { data: comments, mutate } = useSWR(`/posts/${postId}/comments`);

const refreshComments = async () =&amp;gt; {
  // 서버에서 데이터를 강제로 다시 가져와 SWR 캐시를 최신 상태로 업데이트
  await mutate();
};&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;code&gt;mutate()&lt;/code&gt;를 호출하면 서버에서 데이터를 강제로 다시 가져오고, 캐시를 최신 상태로 동기화합니다. 이를 통해 서버의 상태와 클라이언트의 캐시를 일관성 있게 유지할 수 있습니다.&lt;/p&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;mutate를 활용한 상태 관리 최적화&lt;/h2&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;React 애플리케이션에서 &lt;b&gt;&lt;code&gt;mutate&lt;/code&gt;를 사용하면 서버와 클라이언트 간의 데이터 일관성을 유지하면서도, 사용자 경험을 크게 향상시킬 수 있습니다.&lt;/b&gt; 낙관적 업데이트를 통해 빠른 UI 응답을 제공하고, 캐시 데이터를 효율적으로 관리함으로써 불필요한 서버 요청을 줄일 수 있습니다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;또한, &lt;code&gt;mutate&lt;/code&gt;는 서버 상태와의 동기화에 유연하게 대처할 수 있어 실시간 데이터를 처리하는 애플리케이션에서 특히 유용합니다. 사용자 액션에 즉각적으로 반응하는 인터랙티브한 UI를 만들 때, &lt;code&gt;mutate&lt;/code&gt;를 활용하면 성능과 사용자 경험 모두를 최적화할 수 있습니다.&lt;/p&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;결론&lt;/h2&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;code&gt;useSWR&lt;/code&gt;에서 제공하는 &lt;code&gt;mutate&lt;/code&gt; 함수는 캐시 데이터를 수동으로 변경하거나 업데이트할 수 있는 강력한 도구입니다. 이를 통해 클라이언트와 서버 간의 상태를 동기화하고, 즉각적인 UI 업데이트가 필요한 상황에서 매우 유용하게 사용할 수 있습니다. React 애플리케이션에서 &lt;b&gt;데이터 페칭과 상태 관리를 최적화&lt;/b&gt;하고 싶다면, &lt;code&gt;mutate&lt;/code&gt;를 적절히 활용하여 더 나은 사용자 경험을 제공해보세요.&lt;/p&gt;</description>
      <category>React</category>
      <category>mutate</category>
      <category>react</category>
      <category>useSWR</category>
      <author>탄력이</author>
      <guid isPermaLink="true">https://elastinn.tistory.com/13</guid>
      <comments>https://elastinn.tistory.com/13#entry13comment</comments>
      <pubDate>Sun, 6 Oct 2024 17:59:24 +0900</pubDate>
    </item>
    <item>
      <title>SpringBoot 2.7 queryDsl 설정 방법.(java src에 java파일 안생기도록)</title>
      <link>https://elastinn.tistory.com/11</link>
      <description>&lt;h1&gt;SpringBoot 2.7 queryDsl 설정 방법.&lt;/h1&gt;
&lt;blockquote data-ke-style=&quot;style1&quot;&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;나는 김영한 강사님의 queryDsl 강의를 듣고있다.&lt;br /&gt;강의 내용의 springBoot의 버전은 2.6일 것이다.&lt;br /&gt;springBoot 2.7 이상에서는 강의 내용대로는 queryDsl 설정이 안된다는 것을 알 수 있다.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;Unable to load class 'com.mysema.codegen.model.Type'.&lt;/h2&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;김영한 강사님의 queryDsl 강의 내용과 같이 설정했다면&lt;br /&gt;Unable to load class 'com.mysema.codegen.model.Type'.&lt;br /&gt;위와 같은 에러가 발생했을 것이다.&lt;br /&gt;정상 작동하는 설정 방법을 아래 적어겠다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style1&quot;&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;springBoot 2.7이상에서는 어떻게 설정하면 좋을지 알아보자.&lt;br /&gt;(사실 필자는 2.7만 쓰기 때문에 3이상은 아래 설정으로 잘 되는지 모르겠다.)&lt;br /&gt;제 설정 방법을 참고하여 3이상을 설정한 분은 댓글 부탁드립니다.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;build.gradle 설정.&lt;/h2&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;참고한 블로그에 있는 build.gradle 설정을 가져와 실행해보고, 직접 실행해보며 내가 쓰는 설정을 만들었다.&lt;br /&gt;참고 블로그의 내용을 굳이 수정하여 아래와 같이 설정을 쓰는 이유를 적어보겠다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1. 위 말한 Unable to load class 'com.mysema.codegen.model.Type'. 오류가 발생하지 않고 &lt;b&gt;SpringBoot 2.7에서 queryDsl이 정상 작동&lt;/b&gt;한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2. 강의 내용과 같은 경로에 QEntity 파일이 생성이 된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;3. src/main/ 하위에 QEntity 파일이 생성되지 않고,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이미 git ignore 설정이 되어있는 &lt;b&gt;build/ 경로 하위에만 파일이 생성&lt;/b&gt;된다. (git ignore를 따로 설정해줘야하는 번거로움이 없다.)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;pre class=&quot;gradle&quot;&gt;&lt;code&gt;plugins {
    id 'java'
    id 'org.springframework.boot' version '2.7.12'
    id 'io.spring.dependency-management' version '1.0.15.RELEASE'

}

group = 'study'
version = '0.0.1-SNAPSHOT'
sourceCompatibility = '11'

configurations {
    compileOnly {
        extendsFrom annotationProcessor
    }
}

repositories {
    mavenCentral()
}

dependencies {
    implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
    implementation 'org.springframework.boot:spring-boot-starter-web'
    compileOnly 'org.projectlombok:lombok'

    // queryDSL 설정
    implementation &quot;com.querydsl:querydsl-jpa&quot;
    implementation &quot;com.querydsl:querydsl-core&quot;
    implementation &quot;com.querydsl:querydsl-collections&quot;
    annotationProcessor &quot;com.querydsl:querydsl-apt:${dependencyManagement.importedProperties['querydsl.version']}:jpa&quot; // querydsl JPAAnnotationProcessor 사용 지정
    annotationProcessor &quot;jakarta.annotation:jakarta.annotation-api&quot; // java.lang.NoClassDefFoundError (javax.annotation.Generated) 대응 코드
    annotationProcessor &quot;jakarta.persistence:jakarta.persistence-api&quot; // java.lang.NoClassDefFoundError (javax.annotation.Entity) 대응 코드

    runtimeOnly 'com.h2database:h2'
    annotationProcessor 'org.projectlombok:lombok'
    testImplementation 'org.springframework.boot:spring-boot-starter-test'
}

tasks.named('test') {
    useJUnitPlatform()
}

//querydsl 추가 시작
def querydslDir = &quot;$buildDir/generated/querydsl&quot;

// java source set 에 querydsl QClass 위치 추가
sourceSets {
    main.java.srcDirs += [ querydslDir ]
}

// gradle clean 시에 QClass 디렉토리 삭제
clean {
    delete file(querydslDir)
}
//querydsl 추가 끝&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위와 같이 설정하면 SpringBoot 2.7 에서 Unable to load class 'com.mysema.codegen.model.Type'. 오류가 뜨지 않고 정상 작동할 것이다.&lt;br /&gt;이만 글 줄인다. 해당 설정으로 되는 사람, 안되는 사람 모두 댓글 부탁드려요.&lt;/p&gt;</description>
      <category>Java</category>
      <category>querydsl</category>
      <category>QueryDsl설정</category>
      <category>SpringBoot2.7</category>
      <category>Unable to load class 'com.mysema.codegen.model.Type'.</category>
      <author>탄력이</author>
      <guid isPermaLink="true">https://elastinn.tistory.com/11</guid>
      <comments>https://elastinn.tistory.com/11#entry11comment</comments>
      <pubDate>Mon, 5 Jun 2023 16:11:11 +0900</pubDate>
    </item>
    <item>
      <title>[운영체제] 프로세스와 스레드의 개념 및 차이 면접준비</title>
      <link>https://elastinn.tistory.com/10</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;Goal&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;프로세스와 스레드의 개념을 설명할 수 있다.&lt;/li&gt;
&lt;li&gt;프로세스와 스레드의 차이를 이해하고 설명할 수 있다.&lt;/li&gt;
&lt;li&gt;멀티 프로세스 대신 멀티 스레드를 사용하는 이유를 알아본다.&lt;/li&gt;
&lt;/ul&gt;
&lt;h1&gt;프로세스와 스레드의 차이(Process vs Thread)&lt;/h1&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;프로그램 (Program) 이란&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사전적 의미
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&quot;어떤 작업을 위해 실행할 수 있는 파일&quot;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;프로세스(Process)란&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사전적 의미
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&quot;컴퓨터에서 연속적으로 실행되고 있는 컴퓨터 프로그램&quot;&lt;/li&gt;
&lt;li&gt;메모리에 올라와 실행되고 있는 프로그램의 독립적인 객체(인스턴스)&lt;/li&gt;
&lt;li&gt;운영체제로부터 시스템 자원을 할당받는 작업의 단위&lt;/li&gt;
&lt;li&gt;독립적인 address space를 갖고 독립적인 resource를 갖는다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;할당받는 시스템 자원의 예
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;CPU 시간&lt;/li&gt;
&lt;li&gt;운영되기 위해 필요한 주소 공간&lt;/li&gt;
&lt;li&gt;Code, Data, Stack, Heap의 구조로 되어 있는 독립된 메모리 영역&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;특징&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-origin-width=&quot;2991&quot; data-origin-height=&quot;1588&quot; data-filename=&quot;process.png&quot; width=&quot;651&quot; height=&quot;346&quot; data-ke-mobilestyle=&quot;widthOrigin&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cuXzwl/btq8brRfA4R/sUaNJHGNBGk0RojHvYXceK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cuXzwl/btq8brRfA4R/sUaNJHGNBGk0RojHvYXceK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cuXzwl/btq8brRfA4R/sUaNJHGNBGk0RojHvYXceK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcuXzwl%2Fbtq8brRfA4R%2FsUaNJHGNBGk0RojHvYXceK%2Fimg.png&quot; data-origin-width=&quot;2991&quot; data-origin-height=&quot;1588&quot; data-filename=&quot;process.png&quot; width=&quot;651&quot; height=&quot;346&quot; data-ke-mobilestyle=&quot;widthOrigin&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;프로세스는 각각 독립된 메모리 영역(Code, Data, Stack, Heap의 구조)를 할당받는다.&lt;/li&gt;
&lt;li&gt;기본적으로 프로세스당 최소 1개의 스레드(메인 스레드)를 갖는다.&lt;/li&gt;
&lt;li&gt;각 프로세스는 별도의 주소 공간(address space)에서 실행되며, 한 프로세스는 다른 프로세스의 변수나 자료구조에 접근할 수 없다.&lt;/li&gt;
&lt;li&gt;한 프로세스가 다른 프로세스의 자원에 접근하려면 프로세스 간의 통신(IPC, inter-process-communication)을 사용해야 한다.
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;Ex) 파이프, 파일, 소켓 등을 이용한 통신 방법 이용&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;스레드(Thread) 란&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사전적 의미
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&quot;프로세스 내에서 실행되는 여러 흐름의 단위&quot;&lt;/li&gt;
&lt;li&gt;프로세스의 특정한 수행 경로&lt;/li&gt;
&lt;li&gt;프로세스가 할당받은 자원을 이용하는 실행의 단위&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;특징&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-origin-width=&quot;2991&quot; data-origin-height=&quot;1588&quot; data-filename=&quot;thread.png&quot; width=&quot;527&quot; height=&quot;280&quot; data-ke-mobilestyle=&quot;widthOrigin&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/d1c12R/btq8duOm9J1/CwrzP8V5zfoEeImVKjJKWk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/d1c12R/btq8duOm9J1/CwrzP8V5zfoEeImVKjJKWk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/d1c12R/btq8duOm9J1/CwrzP8V5zfoEeImVKjJKWk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fd1c12R%2Fbtq8duOm9J1%2FCwrzP8V5zfoEeImVKjJKWk%2Fimg.png&quot; data-origin-width=&quot;2991&quot; data-origin-height=&quot;1588&quot; data-filename=&quot;thread.png&quot; width=&quot;527&quot; height=&quot;280&quot; data-ke-mobilestyle=&quot;widthOrigin&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;스레드는 프로세스 내에서 각각 Stack만 따로 할당받고 Code, Data, Heap 영역은 공유한다.&lt;/li&gt;
&lt;li&gt;스레드는 한 프로세스 내에서 동작되는 여러 실행의 흐름이므로, 프로세스 내의 주소 공간이나 자원들(힙 공간 등)을 같은 프로세스 내의 스레드끼리 공유하며 실행된다.&lt;/li&gt;
&lt;li&gt;같은 프로세스 안에 있는 여러 스레드들은 같은 힙 공간을 공유한다. 반면에 프로세스는 다른 프로세스의 메모리에 직접 접근할 수 없다.&lt;/li&gt;
&lt;li&gt;각각의 스레드는 별도의 레지스터와 스택을 갖고 있지만, 힙 메모리는 서로 읽고 쓸 수 없다.&lt;/li&gt;
&lt;li&gt;한 스레드가 프로세스 자원을 변경하면, 다른 이웃 스레드(sibling thread)도 그 변경 결과를 즉시 볼 수 있다.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;멀티 프로세스와 멀티 스레드의 차이&lt;/h2&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;멀티 프로세스&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;멀티 프로세싱이란
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;하나의 응용프로그램을 여러 개의 프로세스로 구성하여 각 프로세스가 하나의 작업(태스크)를 처리하도록 하는 것이다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;장점
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;여러 개의 자식 프로세스 중 하나에 문제가 발생하면 그 자식 프로세스만 죽고, 다른 영향이 확산되지 않는다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;단점
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;Context Switching 에서의 오버헤드
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;Context Switching 과정에서 캐쉬 메모리 초기화 등 무거운 작업이 진행되고 많은 시간이 소모되는 등의 오버헤드가 발생하게 된다.&lt;/li&gt;
&lt;li&gt;프로세스는 각각의 독립된 메모리 영역을 할당받았기 때문에 프로세스 사이에서 공유하는 메모리가 없어, Context Switching이 발생하면 캐쉬에 있는 모든 데이터를 모두 리셋하고 다시 캐쉬 정보를 불러와야 한다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;프로세스 사이의 어렵고 복잡한 통신 기법(IPC)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;프로세스는 각각의 독립된 메모리 영역을 할당받았기 때문에 하나의 프로그램에 속하는 프로세스들 사이의 변수를 공유할 수 있다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;참고) Context Switching이란?
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;CPU에서 여러 프로세스를 돌아가면서 작업을 처리하는 데 이 과정을 Context Switching이라 한다.&lt;/li&gt;
&lt;li&gt;구체적으로, 동작 중인 프로세스가 대기를 하면서 해당 프로세스의 상태(Context)를 보관하고, 대기하고 있던 다음 순서의 프로세스가 동작하면서 이전에 보관했던 프로세스의 상태를 복구하는 작업을 뜻한다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;멀티 스레드&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;멀티 스레딩이란
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;하나의 응용프로그램을 여러 개의 스레드로 구성하고 각 스레드로 하여금 하나의 작업을 처리하도록 하는 것이다.&lt;/li&gt;
&lt;li&gt;윈도우, 리눅스 등 많은 운영체제들이 멀티 프로세싱을 지원하고 있지만 멀티 스레딩을 기본으로 하고 있다.&lt;/li&gt;
&lt;li&gt;웹 서버는 대표적인 멀티 스레드 응용 프로그램이다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;장점
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;시스템 자원 소모 감소 (자원의 효율성 증대)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;프로세스를 생성하여 자원을 할당하는 시스템 콜이 줄어들어 자원을 효율적으로 관리할 수 있다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;시스템 처리량 증가 (처리 비용 감소)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;스레드 간 데이터를 주고 받는 것이 간단해지고 시스템 자원 소모가 줄어들게 된다.&lt;/li&gt;
&lt;li&gt;스레드 사이의 작업량이 작아 Context Switching이 빠르다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;간단한 통신 방법으로 인한 프로그램 응답 시간 단축
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;스레드 프로세스 내의 Stack 영역을 제외한 모든 메모리를 공유하기 때문에 통신의 부담이 적다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;멀티 프로세스 대신 멀티 스레드를 사용하는 이유&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;멀티 프로세스 대신 멀티 스레드를 사용하는 것의 의미?
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;쉽게 설명하면, 프로그램을 여러 개 키는 것보다 하나의 프로그램 안에서 여러 작업을 해결하는 것이다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-origin-width=&quot;3844&quot; data-origin-height=&quot;997&quot; data-filename=&quot;multi-thread.png&quot; width=&quot;721&quot; height=&quot;187&quot; data-ke-mobilestyle=&quot;widthOrigin&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bIw2Gr/btq8eHS6D6m/VP3utBXQVRZZkmf1xnLylk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bIw2Gr/btq8eHS6D6m/VP3utBXQVRZZkmf1xnLylk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bIw2Gr/btq8eHS6D6m/VP3utBXQVRZZkmf1xnLylk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbIw2Gr%2Fbtq8eHS6D6m%2FVP3utBXQVRZZkmf1xnLylk%2Fimg.png&quot; data-origin-width=&quot;3844&quot; data-origin-height=&quot;997&quot; data-filename=&quot;multi-thread.png&quot; width=&quot;721&quot; height=&quot;187&quot; data-ke-mobilestyle=&quot;widthOrigin&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;여러 프로세스(멀티 프로세스)로 할 수 있는 작업들을 하나의 프로세스에서 여러 스레드로 나눠가면서 하는 이유?
&lt;ol style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;자원의 효율성 증대
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;멀티 프로세스로 실행되는 작업을 멀티 스레드로 실행할 경우, 프로세스를 생성하여 자원을 할당하는 시스템 콜이 줄어들어 자원을 효율적으로 관리할 수 있다.&lt;/li&gt;
&lt;li&gt;프로세스 간의 Context Switching시 단순히 CPU 레지스터 교체 뿐만 아니라 RAM과 CPU 사이의 캐쉬 메모리에 대한 데이터까지 초기화되므로 오버헤드가 크기 때문&lt;/li&gt;
&lt;li&gt;스레드는 프로세스 내의 메모리를 공유하기 때문에 독립적인 프로세스와 달리 스레드 간 데이터를 주고 받는 것이 간단해지고 시스템 자원 소모가 줄어들게 된다.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;처리 비용 감소 및 응답 시간 단축
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;또한 프로세스 간의 통신 (IPC)보다 스레드 간의 통신이 비용이 적으므로 작업들 간의 통신의 부담이 줄어든다.&lt;/li&gt;
&lt;li&gt;스레드는 Stack 영역을 제외한 모든 메모리를 공유하기 때문&lt;/li&gt;
&lt;li&gt;프로세스 간의 전환 속도보다 스레드 간의 전환 속도가 빠르다.&lt;/li&gt;
&lt;li&gt;Context Switching 시 스레드는 Stack 영역만 처리하기 때문&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;/li&gt;
&lt;li&gt;주의할 점!
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;동기화 문제&lt;/li&gt;
&lt;li&gt;스레드 간의 자원 공유는 전역 변수(데이터 세그먼트)를 이용하므로 함께 상용할 때 충돌이 발생할 수 있음.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;References&lt;/h2&gt;
&lt;blockquote data-ke-style=&quot;style1&quot;&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&lt;a href=&quot;https://gmlwjd9405.github.io/2018/09/14/process-vs-thread.html&quot;&gt;https://gmlwjd9405.github.io/2018/09/14/process-vs-thread.html&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;</description>
      <category>Java</category>
      <author>탄력이</author>
      <guid isPermaLink="true">https://elastinn.tistory.com/10</guid>
      <comments>https://elastinn.tistory.com/10#entry10comment</comments>
      <pubDate>Sun, 27 Jun 2021 23:17:14 +0900</pubDate>
    </item>
    <item>
      <title>프로그래머스 Java Level 1) 모의고사</title>
      <link>https://elastinn.tistory.com/5</link>
      <description>&lt;ul id=&quot;tab&quot; style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;모의고사&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;문제 설명&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;수포자는 수학을 포기한 사람의 준말입니다. 수포자 삼인방은 모의고사에 수학 문제를 전부 찍으려 합니다. 수포자는 1번 문제부터 마지막 문제까지 다음과 같이 찍습니다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1번 수포자가 찍는 방식: 1, 2, 3, 4, 5, 1, 2, 3, 4, 5, ...&lt;br /&gt;2번 수포자가 찍는 방식: 2, 1, 2, 3, 2, 4, 2, 5, 2, 1, 2, 3, 2, 4, 2, 5, ...&lt;br /&gt;3번 수포자가 찍는 방식: 3, 3, 1, 1, 2, 2, 4, 4, 5, 5, 3, 3, 1, 1, 2, 2, 4, 4, 5, 5, ...&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1번 문제부터 마지막 문제까지의 정답이 순서대로 들은 배열 answers가 주어졌을 때, 가장 많은 문제를 맞힌 사람이 누구인지 배열에 담아 return 하도록 solution 함수를 작성해주세요.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;제한 조건&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;시험은 최대 10,000 문제로 구성되어있습니다.&lt;/li&gt;
&lt;li&gt;문제의 정답은 1, 2, 3, 4, 5중 하나입니다.&lt;/li&gt;
&lt;li&gt;가장 높은 점수를 받은 사람이 여럿일 경우, return하는 값을 오름차순 정렬해주세요.&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;입출력 예&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;answersreturn&lt;/p&gt;
&lt;table style=&quot;border-collapse: collapse; width: 100%;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;[1,2,3,4,5]&lt;/td&gt;
&lt;td&gt;[1]&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;[1,3,2,4,2]&lt;/td&gt;
&lt;td&gt;[1,2,3]&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;입출력 예 설명&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;입출력 예 #1&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;수포자 1은 모든 문제를 맞혔습니다.&lt;/li&gt;
&lt;li&gt;수포자 2는 모든 문제를 틀렸습니다.&lt;/li&gt;
&lt;li&gt;수포자 3은 모든 문제를 틀렸습니다.&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;따라서 가장 문제를 많이 맞힌 사람은 수포자 1입니다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;입출력 예 #2&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;모든 사람이 2문제씩을 맞췄습니다.&lt;/li&gt;
&lt;/ul&gt;
&lt;hr contenteditable=&quot;false&quot; data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style5&quot; /&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;&lt;span style=&quot;color: #ee2323;&quot;&gt;문제풀이&lt;/span&gt;&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;조건 몇가지를 살펴보자.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1. 찍는 방식이 수포자1,2,3 각자 정해져있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2. 문제 갯수는 매개변수로 정해진다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;3. 찍는 방식과 문제 갯수는 배열의 크기가 다르다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;4. 출력 방식은 몇번 수포자가 1등인지 출력한다. 동점자가 있으면 동점자도 출력한다. (오름차순으로)&lt;/p&gt;
&lt;pre id=&quot;code_1623978708190&quot; class=&quot;java&quot; style=&quot;display: block; overflow: auto; padding: 20px; color: #383a42; background: #f8f8f8; font-size: 14px; font-family: 'SF Mono', Menlo, Consolas, Monaco, monospace; border: 1px solid #ebebeb; line-height: 1.71; margin: 20px auto 0px; cursor: default; z-index: 1; font-style: normal; font-variant-ligatures: normal; font-variant-caps: normal; font-weight: 400; letter-spacing: normal; orphans: 2; text-align: start; text-indent: 0px; text-transform: none; widows: 2; word-spacing: 0px; -webkit-text-stroke-width: 0px; text-decoration-thickness: initial; text-decoration-style: initial; text-decoration-color: initial;&quot; data-ke-language=&quot;java&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;class Solution {
    public int[] solution(int[] answers) {
    	 //수포자 1,2,3 이 문제를 찍는 방식
         int[] ex1 = {1, 2, 3, 4, 5};
    	 int[] ex2 = {2, 1, 2, 3, 2, 4, 2, 5};
    	 int[] ex3 = {3, 3, 1, 1, 2, 2, 4, 4, 5, 5};
         
         // 출제 문제 갯수에 맞는 수포자들의 답안지(배열) 생성
    	 int[] supo1 = new int[answers.length];
    	 int[] supo2 = new int[answers.length];
    	 int[] supo3 = new int[answers.length];
    	 int k = 0;
         
         // 수포자들의 답안지에 각자의 문제 찍는 방식으로 답안지 내용을 채워준다.
    	 for(int i=0; i&amp;lt;answers.length;i++) {
    		 k = i%ex1.length;
    		 supo1[i]=ex1[k];
    	 }
    	 for(int i=0; i&amp;lt;answers.length;i++) {
    		 k = i%ex2.length;
    		 supo2[i]=ex2[k];
    	 }
    	 for(int i=0; i&amp;lt;answers.length;i++) {
    		 k = i%ex3.length;
    		 supo3[i]=ex3[k];
    	 }
         
         //맞은 답의 갯수를 세주는 변수 선언
         int count1 =0;
         int count2 =0;
         int count3 =0;
         
         // 맞은 답 있을 때마다 1씩 추가
         for(int i=0; i&amp;lt;answers.length;i++) {
        	 if(answers[i] == supo1[i]) {
        		 count1++;
        	 }
        	 if(answers[i] == supo2[i]) {
        		 count2++;
        	 }
        	 if(answers[i] == supo3[i]) {
        		 count3++;
        	 }
         }
         
        int[] answer;
        
        // count를 비교해 가장 많이 맞은 사람만 출력되도록 if문 돌림
         if(count1&amp;gt;count2) {
        	 if(count1&amp;gt;count3) {
        		 answer = new int[1];
        		 answer[0] = 1;
        	 } else if(count1==count3) {
        		 answer = new int[2];
        		 answer[0] =1;
        		 answer[1] =3;
        	 } else {
        		 answer = new int[1];
        		 answer[0] = 3;
        	 }
         } else if(count1==count2) {
        	 if(count1&amp;gt;count3) {
        		 answer = new int[2];
        		 answer[0] =1;
        		 answer[1] =2;
        	 } else if(count1==count3) {
        		 answer = new int[3];
        		 answer[0] =1;
        		 answer[1] =2;
        		 answer[2] =3;
        	 } else {
        		 answer = new int[1];
        		 answer[0] = 3;
        	 }
         } else {
        	 if(count2&amp;gt;count3) {
        		 answer = new int[1];
        		 answer[0] = 2;
        	 } else if(count2==count3) {
        		 answer = new int[2];
        		 answer[0] =2;
        		 answer[1] =3;
        	 } else {
        		 answer = new int[1];
        		 answer[0] = 3;
        	 }
         }
        
        return answer;
    }
}&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;풀이 절차.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1. 문제 갯수에 맞는 수포자들의 답안지를 작성한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2. 비교해서 맞은 갯수를 센다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;3. 맞은 갯수를 비교해 1등이 누구인지 , 동점자가 있는지 알아내 출력한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;풀이절차를 이렇게 쓰면 너무도 쉬워보인다. 그런데 그걸 자바언어로 하는게 참으로 어려운 것 같다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;더 깔끔하게 다듬어서 코드를 올릴 수도 있겠지만, 어떻게 알고리즘을 떠올렸는지 보려면 바로 답을 맞춘 코드가 더 좋은 것 같다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;필자는 수포자들의 찍는 방식과 문제 갯수가 다르다는 조건이 힘들었다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;찍는 방식을 반복해서 다른 크기의 배열에 넣어야하니까.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;계속 고민하다가 나머지를 생각해냈다. 찍는방식의 배열 크기만큼 나누면 반복 되니까.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그 이후는 잘 풀렸던 것 같다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그러나 출력방식에 맞게 정렬, 동점자 출력이 어려웠지만 많은 if문으로 떼웠다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;다음부턴 다른 함수를 써서 저 부분을 줄여볼 수 있겠다.&lt;/p&gt;</description>
      <category>알고리즘 코딩테스트</category>
      <author>탄력이</author>
      <guid isPermaLink="true">https://elastinn.tistory.com/5</guid>
      <comments>https://elastinn.tistory.com/5#entry5comment</comments>
      <pubDate>Fri, 18 Jun 2021 10:32:47 +0900</pubDate>
    </item>
    <item>
      <title>$.ajax()</title>
      <link>https://elastinn.tistory.com/3</link>
      <description>&lt;div class=&quot;colorscripter-code&quot; style=&quot;color: #f0f0f0; font-family: Consolas, 'Liberation Mono', Menlo, Courier, monospace !important; position: relative !important; overflow: auto;&quot;&gt;
&lt;table class=&quot;colorscripter-code-table&quot; style=&quot;margin: 0px; padding: 0px; border: none; background-color: #272727; border-radius: 4px; height: 463px;&quot; width=&quot;504&quot; cellspacing=&quot;0&quot; cellpadding=&quot;0&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&quot;padding: 6px; border-right: 2px solid #4f4f4f; width: 18px;&quot;&gt;
&lt;div style=&quot;margin: 0; padding: 0; word-break: normal; text-align: right; color: #aaa; font-family: Consolas, 'Liberation Mono', Menlo, Courier, monospace !important; line-height: 130%;&quot;&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;1&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;2&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;3&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;4&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;5&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;6&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;7&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;8&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;9&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;10&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;11&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;12&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;13&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;14&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;15&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;16&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;17&lt;/div&gt;
&lt;div style=&quot;line-height: 130%;&quot;&gt;18&lt;/div&gt;
&lt;/div&gt;
&lt;/td&gt;
&lt;td style=&quot;padding: 6px 0px; text-align: left; width: 455px;&quot;&gt;
&lt;div style=&quot;margin: 0; padding: 0; color: #f0f0f0; font-family: Consolas, 'Liberation Mono', Menlo, Courier, monospace !important; line-height: 130%;&quot;&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&lt;span style=&quot;color: #aaffaa;&quot;&gt;&lt;/span&gt;&lt;span style=&quot;color: #ff3399;&quot;&gt;&amp;lt;&lt;/span&gt;script&lt;span style=&quot;color: #aaffaa;&quot;&gt;&lt;/span&gt;&lt;span style=&quot;color: #ff3399;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;$(&lt;span style=&quot;color: #ffd500;&quot;&gt;'#btn1'&lt;/span&gt;).on(&lt;span style=&quot;color: #ffd500;&quot;&gt;'click'&lt;/span&gt;,&amp;nbsp;&lt;span style=&quot;color: #ff3399;&quot;&gt;function&lt;/span&gt;(){&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;$.ajax({&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;url:&amp;nbsp;&lt;span style=&quot;color: #ffd500;&quot;&gt;&quot;serialize&quot;&lt;/span&gt;,&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;type:&amp;nbsp;&lt;span style=&quot;color: #ffd500;&quot;&gt;&quot;POST&quot;&lt;/span&gt;,&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;data:&amp;nbsp;$(&lt;span style=&quot;color: #ffd500;&quot;&gt;&quot;#frm&quot;&lt;/span&gt;).serialize(),&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;success:&amp;nbsp;&lt;span style=&quot;color: #ff3399;&quot;&gt;function&lt;/span&gt;(data){&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span style=&quot;color: #4be6fa;&quot;&gt;console&lt;/span&gt;.log($(&lt;span style=&quot;color: #ffd500;&quot;&gt;&quot;#frm&quot;&lt;/span&gt;).serialize());&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;$(&lt;span style=&quot;color: #ffd500;&quot;&gt;&quot;#result&quot;&lt;/span&gt;).append(data);&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;},&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;error:&amp;nbsp;&lt;span style=&quot;color: #ff3399;&quot;&gt;function&lt;/span&gt;(data){&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span style=&quot;color: #4be6fa;&quot;&gt;alert&lt;/span&gt;(&lt;span style=&quot;color: #ffd500;&quot;&gt;&quot;serialize&amp;nbsp;err&quot;&lt;/span&gt;);&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span style=&quot;color: #4be6fa;&quot;&gt;console&lt;/span&gt;.log($(&lt;span style=&quot;color: #ffd500;&quot;&gt;&quot;#frm&quot;&lt;/span&gt;).serialize());&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;});&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;});&lt;/div&gt;
&lt;div style=&quot;padding: 0 6px; white-space: pre; line-height: 130%;&quot;&gt;&lt;span style=&quot;color: #aaffaa;&quot;&gt;&lt;/span&gt;&lt;span style=&quot;color: #ff3399;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #aaffaa;&quot;&gt;&lt;/span&gt;&lt;span style=&quot;color: #ff3399;&quot;&gt;/&lt;/span&gt;script&lt;span style=&quot;color: #aaffaa;&quot;&gt;&lt;/span&gt;&lt;span style=&quot;color: #ff3399;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div style=&quot;text-align: right; margin-top: -13px; margin-right: 5px; font-size: 9px; font-style: italic;&quot;&gt;&lt;a style=&quot;color: #4f4f4ftext-decoration:none;&quot; href=&quot;http://colorscripter.com/info#e&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot;&gt;Colored by Color Scripter&lt;/a&gt;&lt;/div&gt;
&lt;/td&gt;
&lt;td style=&quot;vertical-align: bottom; padding: 0px 2px 4px 0px; width: 15px;&quot;&gt;&lt;a style=&quot;text-decoration: none; color: white;&quot; href=&quot;http://colorscripter.com/info#e&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot;&gt;&lt;span style=&quot;font-size: 9px; word-break: normal; background-color: #4f4f4f; color: white; border-radius: 10px; padding: 1px;&quot;&gt;cs&lt;/span&gt;&lt;/a&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/div&gt;</description>
      <category>Java</category>
      <author>탄력이</author>
      <guid isPermaLink="true">https://elastinn.tistory.com/3</guid>
      <comments>https://elastinn.tistory.com/3#entry3comment</comments>
      <pubDate>Sun, 16 May 2021 19:08:08 +0900</pubDate>
    </item>
  </channel>
</rss>