<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
    <channel>
        <title>aid_choi.log</title>
        <link>https://velog.io/</link>
        <description>KMU Software 21</description>
        <lastBuildDate>Sat, 07 Jan 2023 04:52:23 GMT</lastBuildDate>
        <docs>https://validator.w3.org/feed/docs/rss2.html</docs>
        <generator>https://github.com/jpmonette/feed</generator>
        <image>
            <title>aid_choi.log</title>
            <url>https://images.velog.io/images/aid_choi/profile/0eeebe2e-16ec-4e7b-bdc7-6b567525d117/kmu고양이.jpg</url>
            <link>https://velog.io/</link>
        </image>
        <copyright>Copyright (C) 2019. aid_choi.log. All rights reserved.</copyright>
        <atom:link href="https://v2.velog.io/rss/aid_choi" rel="self" type="application/rss+xml"/>
        <item>
            <link>https://velog.io/@aid_choi/9zqqze5c</link>
            <guid>https://velog.io/@aid_choi/9zqqze5c</guid>
            <pubDate>Sat, 07 Jan 2023 04:52:23 GMT</pubDate>
            <description><![CDATA[<p><img src="https://velog.velcdn.com/images/aid_choi/post/cf1767e4-8057-4f62-ac3d-fe5503f72b09/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/aid_choi/post/810e21b8-84a4-4818-a3f5-db9026fe8e99/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <link>https://velog.io/@aid_choi/6uj6e71b</link>
            <guid>https://velog.io/@aid_choi/6uj6e71b</guid>
            <pubDate>Sat, 07 Jan 2023 04:41:24 GMT</pubDate>
            <description><![CDATA[<p><img src="https://velog.velcdn.com/images/aid_choi/post/623f8c70-c94b-4c06-911b-b3fae353ca18/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[Google 애널리틱스] 내 깃허브 페이지랑 연동하기!]]></title>
            <link>https://velog.io/@aid_choi/Google-%EC%95%A0%EB%84%90%EB%A6%AC%ED%8B%B1%EC%8A%A4-%EB%82%B4-%EA%B9%83%ED%97%88%EB%B8%8C-%ED%8E%98%EC%9D%B4%EC%A7%80%EB%9E%91-%EC%97%B0%EB%8F%99%ED%95%98%EA%B8%B0</link>
            <guid>https://velog.io/@aid_choi/Google-%EC%95%A0%EB%84%90%EB%A6%AC%ED%8B%B1%EC%8A%A4-%EB%82%B4-%EA%B9%83%ED%97%88%EB%B8%8C-%ED%8E%98%EC%9D%B4%EC%A7%80%EB%9E%91-%EC%97%B0%EB%8F%99%ED%95%98%EA%B8%B0</guid>
            <pubDate>Thu, 16 Dec 2021 14:25:52 GMT</pubDate>
            <description><![CDATA[<h2 id="서론">서론</h2>
<p>우리가 이용하고 있는 깃허브 페이지를 잘 관리하고 있는지 어떻게 확인할 수 있을까?</p>
<p>많은 방법들이 있겠지만 이번 시간에는 Google 애널리틱스를 이용해보려고 한다.</p>
<p>그렇다면 Google 애널리틱스는 무엇일까?</p>
<br>

<h2 id="google-애널리틱스">Google 애널리틱스?</h2>
<p><img src="https://images.velog.io/images/aid_choi/post/db5173a6-3016-44ca-85e1-ad2ec770d41d/image.png" alt=""></p>
<blockquote>
<p>구글 마케팅 플랫폼 브랜드 내의 플랫폼
웹사이트 트래픽을 추적하고 보고하는 구글이 제공하는 웹 애널리틱스 서비스</p>
</blockquote>
<p>그렇다면 이러한 구글 애널리틱스를 어떻게 우리 깃허브 페이지에 적용할 수 있을까?</p>
<p>아래에서 자세하게 다뤄보도록 할 것이다!</p>
<br>

<h2 id="google-애널리틱스-깃허브-페이지에-적용하기">Google 애널리틱스 깃허브 페이지에 적용하기!</h2>
<br>

<h4 id="google-애널리틱스-공식-홈페이지-주소--httpsanalyticsgooglecom">Google 애널리틱스 공식 홈페이지 주소 : <a href="https://analytics.google.com/">https://analytics.google.com/</a></h4>
<br>

<p>사용하는 Google 계정이 없는 경우, 애널리틱스에 사용할 새로운 계정을 이용!</p>
<p>기존에 사용하는 계정이 있는 경우, 해당 계정으로 사이트에서 로그인하여 이용!</p>
<p><img src="https://images.velog.io/images/aid_choi/post/39ab4167-9579-4157-a5a6-e26353c389f3/image.png" alt=""></p>
<p>속성 열에서 속성 만들기를 클릭한 뒤</p>
<p>속성 이름 / 시간대 / 통화를 본인에게 맞게 설정해준다</p>
<br>

<p>이때 추적 ID로 G-가 아닌 UA-가 필요한 경우에는 아래를 따른다</p>
<p>(long haul 테마의 경우 UA-가 필요하기 때문에 아래를 따름)</p>
<p><img src="https://images.velog.io/images/aid_choi/post/b012fb03-0af1-45a9-965a-2df6dde38cb0/image.png" alt=""></p>
<p>고급 옵션 보기를 누른 뒤</p>
<p>유니버설 애널리틱스 속성 만들기 ON</p>
<p>본인의 깃허브 페이지 URL을 복사한 뒤에 붙여넣기</p>
<p>유니버설 애널리틱스 속성만 만들기 클릭!</p>
<p><img src="https://images.velog.io/images/aid_choi/post/186aa42d-22bb-4652-9706-9f4286a1e448/image.png" alt=""></p>
<p>후에 나오는 비즈니스 정보(업종 / 비즈니스 규모 / 사용계획)은 본인에게 맞게 설정!</p>
<p>위 과정을 다 끝내면 추적 아이디를 얻어낼 수 있음!</p>
<p>얻어낸 추적 아이디를 아래 코드를 바꾸어 작성하는 것으로 완료 가능
(long haul 템플릿을 기준으로 작성한 점을 유의할 것!)</p>
<p><img src="https://images.velog.io/images/aid_choi/post/99eac0b6-fa1c-489f-8a86-be154d56754c/image.png" alt=""></p>
<p>_config.yml의 30번째 줄, google_analytics에 해당하는 추적 아이디를 입력</p>
<p><img src="https://images.velog.io/images/aid_choi/post/3864af10-7473-46fb-8c77-c0335ffef3e5/image.png" alt=""></p>
<p>이렇게 되었다면 깃허브 홈페이지에 구글 애널리틱스 연동 끝<del>!</del>!</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[Markdown] 무엇에 쓰는 물건인고]]></title>
            <link>https://velog.io/@aid_choi/Markdown-%EB%AC%B4%EC%97%87%EC%97%90-%EC%93%B0%EB%8A%94-%EB%AC%BC%EA%B1%B4%EC%9D%B8%EA%B3%A0</link>
            <guid>https://velog.io/@aid_choi/Markdown-%EB%AC%B4%EC%97%87%EC%97%90-%EC%93%B0%EB%8A%94-%EB%AC%BC%EA%B1%B4%EC%9D%B8%EA%B3%A0</guid>
            <pubDate>Wed, 15 Dec 2021 13:33:09 GMT</pubDate>
            <description><![CDATA[<h2 id="서론">서론</h2>
<p> 소프트웨어학부의 학부생으로 지내면서 .md나 .markdown이라는 확장자를 여러 곳에서 흔하게 볼 수 있었다. 누구나 쉽게 공감할 수 있는 대표적인 예는 아마 GitHub에서 주로 이용하는 README.md가 아닐까 싶다. 그렇다면 markdown은 무엇을 의미하는 것일까?
<br><br></p>
<h2 id="markdown마크다운이란">Markdown(마크다운)이란?</h2>
<p><img src="https://images.velog.io/images/aid_choi/post/7a1b4711-f244-4800-8c08-1ceb85f272bd/image.png" alt=""></p>
<blockquote>
<p>Markdown(마크다운)은 일반 텍스트 문서의 양식을 편집하는 문법을 의미함.
README파일, 온라인 문서, 일반 텍스트 편집기로 문서 양식을 편집할 때 이용됨.
이러한 마크다운을 이용해 작성된 문서는 쉽게 다른 문서 형태(ex. HTML)로 변환이 가능함.</p>
</blockquote>
<p>또한, 우리가 이용하고 있는 깃허브 페이지 역시 지킬 기반이기 때문에 마크다운을 알면 쉽게 포스트를 작성할 수 있음!</p>
<p>(필자가 주로 사용하는 블로그인 velog 역시도 마크다운 기반으로 포스트를 작성하는 공통점이 있음)
<br><br></p>
<h2 id="어떻게-쓰는-물건인고">어떻게 쓰는 물건인고</h2>
<h3 id="1-제목header">1. 제목(header)</h3>
<p>h1 ~ h6 까지 존재함. #의 개수에 따라 나뉘어짐.</p>
<h1 id="h1">h1</h1>
<h2 id="h2">h2</h2>
<h3 id="h3">h3</h3>
<h4 id="h4">h4</h4>
<h5 id="h5">h5</h5>
<h6 id="h6">h6</h6>
<br>

<h3 id="2-문단-간격">2. 문단 간격</h3>
<p>문단의 간격을 &#39;줄바꿈&#39;을 통해 나타냄.</p>
<p>여러 줄의 줄바꿈을 구현하고 싶을 때는 <code>&lt;br&gt;</code>을 이용
<br></p>
<h3 id="3-폰트-스타일">3. 폰트 스타일</h3>
<p>굵게, 기울이기, 취소선 등의 스타일을 아래처럼 표현할 수 있음.</p>
<p><code>__굵게__</code> : <strong>굵게</strong></p>
<p><code>**굷게**</code> : <strong>굷게</strong></p>
<p><code>_기울이기_</code> : <em>기울이기</em></p>
<p><code>*기울이기*</code> : <em>기울이기</em></p>
<p><code>~~취소선~~</code> : <del>취소선</del>
<br></p>
<h3 id="4-인용문-작성">4. 인용문 작성</h3>
<p>인용문을 작성할 때는 <code>&gt;</code>을 이용함.</p>
<blockquote>
<p>이런 식으로 적용되며</p>
<blockquote>
<p><code>&gt;</code>의 개수에 따라 중첩하는 것이 가능함</p>
<blockquote>
<blockquote>
<blockquote>
<p>개수에 제한이 없는 중첩문을 볼 수 있음</p>
</blockquote>
</blockquote>
</blockquote>
</blockquote>
</blockquote>
]]></description>
        </item>
        <item>
            <title><![CDATA[[Jekyll] 정적 홈페이지와 Jekyll는 무엇일까?]]></title>
            <link>https://velog.io/@aid_choi/Jekyll-%EC%A0%95%EC%A0%81-%ED%99%88%ED%8E%98%EC%9D%B4%EC%A7%80%EC%99%80-Jekyll%EB%8A%94-%EB%AC%B4%EC%97%87%EC%9D%BC%EA%B9%8C</link>
            <guid>https://velog.io/@aid_choi/Jekyll-%EC%A0%95%EC%A0%81-%ED%99%88%ED%8E%98%EC%9D%B4%EC%A7%80%EC%99%80-Jekyll%EB%8A%94-%EB%AC%B4%EC%97%87%EC%9D%BC%EA%B9%8C</guid>
            <pubDate>Tue, 14 Dec 2021 14:07:21 GMT</pubDate>
            <description><![CDATA[<h2 id="서론">서론</h2>
<p>학부 수업 시간을 통해 만들게된 GitHub Page는 Jekyll 기반의 정적 홈페이지이다.
사실 Jekyll 이라는 것도 정적 홈페이지라는 단어도 많은 사람들에게는 생소할 것이다.
오늘은 정적 홈페이지는 무엇이고 Jekyll 은 어떤 역할을 하는 지 알아볼 것이다.</p>
<p>정적 홈페이지와 반대되는 개념인 동적 홈페이지를 함께 비교하며 설명해볼 것이다. 
<br><br></p>
<h2 id="정적-홈페이지란">정적 홈페이지란?</h2>
<p><img src="https://images.velog.io/images/aid_choi/post/0e1b6e58-3588-4f8f-a46a-aa72cc91ae59/image.png" alt=""></p>
<blockquote>
<p>정적 웹 페이지</p>
<ul>
<li>서버에 미리 저장된 파일이 그대로 전달되는 웹 페이지</li>
<li>서버는 사용자의 요청에 해당하는 저장된 웹 페이지를 보냄</li>
<li>사용자는 서버에 저장된 데이터가 변경되지 않는 한 고정된 웹 페이지를 보게 됨</li>
</ul>
</blockquote>
<p><br><br></p>
<h2 id="동적-홈페이지란">동적 홈페이지란?</h2>
<p><img src="https://images.velog.io/images/aid_choi/post/a0d2278f-72e9-4516-ae86-4faa852a6415/image.png" alt=""></p>
<blockquote>
<p>동적 웹 페이지</p>
<ul>
<li>서버에 있는 데이트들을 스크립트에 의해 가공처리한 후 생성되어 전달되는 웹 페이지</li>
<li>서버는 사용자의 요청을 해석하여 데이터를 가공한 후 생성되는 웹 페이지를 보냄</li>
<li>사용자는 상황, 시간, 요청 등에 따라 달라지는 웹 페이지를 보게 됨</li>
</ul>
</blockquote>
<p><br><br></p>
<h2 id="정적-vs-동적">정적 vs 동적!</h2>
<p>그렇다면 정적 홈페이지와 동적 홈페이지는 어떤 점이 다를까?
단점과 장점을 통해 알아보도록 하자
<br></p>
<ul>
<li><p>정적 웹 페이지의 장점</p>
<ul>
<li>빠름: 요청에 대한 파일만 전송하면 되기 때문에 추가적인 작업이 없음</li>
<li>적은 비용: 웹 서버 구축 비용만이 고려대상이 됨</li>
</ul>
</li>
<li><p>정적 웹 페이지의 단점</p>
<ul>
<li>한정성: 저장된 정보만을 사용자에게 보여줄 수 있음</li>
<li>관리가 힘듦: 추가/수정/삭제의 작업 모두 수동으로 이루어짐</li>
</ul>
</li>
<li><p>동적 웹 페이지의 장점</p>
<ul>
<li>다양성: 다양한 정보를 조합하여 동적으로 생성하여 제공 가능함</li>
<li>관리가 쉬움: 웹 사이트 구조에 따른 추가/수정/삭제의 작업들이 모두 용이함</li>
</ul>
</li>
<li><p>동적 웹 페이지의 단점</p>
<ul>
<li>느림: 사용자에게 웹 페이지를 전달하기 전 전처리가 필요함</li>
<li>추가 비용: 웹 서버 구축 비용 이외 추가적 처리를 위한 어플리케이션 서버가 필요함
<br><br><h2 id="그렇다면-jekyll은-무엇일까">그렇다면 Jekyll은 무엇일까?</h2>
<img src="https://images.velog.io/images/aid_choi/post/524fe552-016a-4352-90e6-0dfa3abd9294/image.png" alt="">
jekyll(이하 지킬)은 웹 사이트 개발 툴이라고 함
지킬은 개발자와 연구자들이 가장 많이 이용하는 서비스인 깃허브에서 개발한 사이트 개발 툴임</li>
</ul>
</li>
</ul>
<p>사이트 개발과 블로그 툴로 유명한 것으로는 워드프레스(Wordpress)가 있음
하지만 여러 영향력을 이유로 워드프레스에서 지킬로의 많은 사이트 이동이 이루어지고 있음</p>
<p>지킬로의 사이트 이동이 이루어지는 가장 큰 이유는 &#39;동적 웹 페이지&#39;이기 때문!</p>
<p>위에서 언급한 동적 웹 페이지의 장점 &#39;빠르다&#39;와 &#39;가볍다&#39;이 모든 이유를 대변할 수 있다고 함</p>
<p>특히 Markdown이라는 온라인 문서 편집 표준 양식을 따르기 때문에 깃허브 ReadMe 파일과 동일한 방법으로 작성할 수 있기 때문에 글 작성에 있어서 편안함을 느낄 수 있음.
<br><br></p>
<h2 id="간단한-jekyll-사용법을-알아보자">간단한 Jekyll 사용법을 알아보자</h2>
<p>아래와 같은 간단한 명령어로 개인의 사이트를 만들 수 있다.</p>
<blockquote>
<p><code>gem install bundler jekyll</code>
<code>jekyll new my-web-site</code>
<code>cd my-web-site</code></p>
</blockquote>
<p>이외 지킬 설치는 Ubuntu와 Window에서 방법이 다르기 때문에 자세한 내용들은 지킬의 공식 홈페이지를 참고하는 것이 좋을 것이다</p>
<p>지킬 공식 홈페이지 주소 : <a href="https://jekyllrb-ko.github.io/">https://jekyllrb-ko.github.io/</a></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[Git] Git과 GitHub 알아보기!]]></title>
            <link>https://velog.io/@aid_choi/Git-Git%EA%B3%BC-GitHub-%EC%95%8C%EC%95%84%EB%B3%B4%EA%B8%B0</link>
            <guid>https://velog.io/@aid_choi/Git-Git%EA%B3%BC-GitHub-%EC%95%8C%EC%95%84%EB%B3%B4%EA%B8%B0</guid>
            <pubDate>Tue, 14 Dec 2021 13:09:15 GMT</pubDate>
            <description><![CDATA[<h2 id="서론">서론</h2>
<p>Git/GitHub, 소프트웨어학부에 진학하기 전에는 한 번도 들어보지 못한
이름부터 굉장히 낯설고 생소했던 친구들이지만 최근에 들어서 매일매일
찾아 사용하는 친구들이지만 정확한 정의, 역할, 용도를 모르는 것 같아
Git/GitHub에 대하여 수업에 배운 내용 + 추가 조사한 내용으로 정리하고자 한다!</p>
<h2 id="git은-무엇일까">Git은 무엇일까?</h2>
<p><img src="https://images.velog.io/images/aid_choi/post/493bc853-9898-45c6-aebd-bbd3079c0776/image.png" alt=""></p>
<blockquote>
<p>Git은 형상 관리 도구 중 하나로, 컴퓨터 파일의 변경사항을 추적하고 여러 명의 사용자들 간에 해당 파일들의 작업을 조율하기 위한 분산 버전 관리 시스템이다.</p>
</blockquote>
<ul>
<li>Git은 소프트웨어 개발에서 소스 코드를 효과적으로 관리할 수 있도록 하는 무료, 공개 소프트웨어.</li>
<li>Git은 프로젝트 폴더 내에서 작업을 기록하고, 버전 관리를 통해 체계적인 개발이 가능하도록 한다.</li>
<li>Git 공식 홈페이지에서 더 자세한 설명이 가능함 -&gt; <a href="https://discord.gg/mP4DEqHK">https://discord.gg/mP4DEqHK</a></li>
</ul>
<br>

<h2 id="git의-장점은">Git의 장점은?!</h2>
<p>이러한 Git을 장점을 중심으로 다시 간단하게 정리해보면
소스 코드를 따로 주고 받을 필요 없이, Git을 사용하면 동일한 하나의 프로젝트, 같은 파일을 여러 명의 사람들이 동시에 작업하는 병렬 개발을 가능하게 해준다는 것!
그렇다면 Git과 이름이 비슷한 GitHub는 과연 무엇일까? 같이 알아보도록 하자!
<br></p>
<h2 id="github란">GitHub란?</h2>
<p><img src="https://images.velog.io/images/aid_choi/post/39a695b9-bebc-4de1-9437-a9f7cc0d6446/image.png" alt=""></p>
<blockquote>
<p>GitHub는 분산 버전 관리 툴인 Git을 사용하는 프로젝트를 지원하는 웹 호스팅 서비스이다.</p>
</blockquote>
<p>GitHub는 버전 관리와 협업을 위한 코드 웹 호스팅 플랫폼으로 시간과 장소에 구애받지 않고 협업 프로젝트를 진행할 수 있도록 도와주는 도우미의 역할을 해준다고 보면 편함.
<br></p>
<hr>
<br>

<h2 id="github를-한-번-이용해볼까">GitHub를 한 번 이용해볼까?</h2>
<p>GitHub를 이용하기 전, 자주 이용되는 간단한 용어를 정리해보면 다음과 같다.</p>
<ol>
<li>Repository : 파일이나 디렉토리를 저장해두는 저장소를 말함.</li>
<li>Commit : 파일을 추가, 변경한 이력을 저장소에 기록, 저장하는 작업을 말함.</li>
<li>Push : Commit을 위해 추가, 변경한 내용을 원격 저장소에 업로드하는 작업을 말함.</li>
</ol>
<h4 id="1-repository-생성">1. Repository 생성</h4>
<p><img src="https://images.velog.io/images/aid_choi/post/d3c3a23d-2daa-416e-b1a7-aa96a9dacf7a/image.png" alt="">
사진에서 오른쪽 상단의 초록색깔 New 버튼을 한 번 클릭해준다.
버튼을 클릭하게 되면 Repository 생성 화면으로 이동하게 된다.</p>
<p><img src="https://images.velog.io/images/aid_choi/post/20fd02f9-0d71-40d4-89a1-77f0ac7e211b/image.png" alt="">
Repository 생성 화면에서 사용자가 원하는 저장소 이름 / 설명(선택) / 옵션 을 선택할 수 있음.</p>
<ul>
<li>초기에는 무료 사용자는 Private를 이용할 수 없었지만 2019년 말부터 무료 사용자도 Private 옵션을 사용할 수 있도록 변경되면서 비공개 리포지토리 생성이 가능하게 됨.</li>
</ul>
<h4 id="2-git-초기-설정">2. Git 초기 설정</h4>
<p>Git이 컴퓨터에 설치했다면 사용자 이름과 사용자 이메일 주소를 설정하는 것으로 이용 준비를 할 수 있음.</p>
<blockquote>
<p><code>git config --global user.name &quot;사용자 이름&quot;</code>
<code>git config --global user.email &quot;사용자 이메일&quot;</code></p>
</blockquote>
<p>위 두 개의 명령어를 차례대로 이용하여 Git을 이용한 프로젝트를 진행할 수 있음.</p>
<p>아래 설정들은 위 2가지 기본 설정 이후, 세부 정보라고 이해하면 편함.</p>
<ol>
<li><p><code>cd 폴더 경로</code>
GitHub 웹페이지의 저장소, 즉 원격저장소와 내 컴퓨터 내의 저장소인 로컬 저장소를 연결하기 위해서는 로컬 저장소를 만들 경로로 이동해야 하는데 이때 cd 명령어를 사용함.</p>
</li>
<li><p><code>git init</code>
해당 프로젝트를 Git의 리포지토리로 만들기 위한 명령어라고 이해하면 됨.</p>
</li>
<li><p><code>git remote add origin 원격 저장소 주소</code>
git remote는 원격 저장소를 관리하는 명령어임.
<code>git remote -v</code> 명령어를 통해서 현재 커넥트되어 있는 원격 저장소가 무엇인지 확인할 수 있음.</p>
</li>
<li><p><code>git clone 저장소 주소</code>
GitHub에 리포지토리나 서버의 프로젝트를 그대로 내려받는 명령어임.</p>
<br>
<hr>
<br>

</li>
</ol>
<p>초기에 Git과 GitHub를 이용하면서 많이 어려움을 겪었던 부분들을 다시 정리해본 포스팅이었음.</p>
<p>또한, 이러한 GitHub의 이용 역시 명령어로 이용하는 것이 아닌 간단한 버튼의 조작으로도 commit, push 등이 가능하게 도와주는 도구 역시 존재함!</p>
<p>아래는 필자가 애용하고 있는 GitHub Desktop 다운로드 주소인데 GitHub의 이용이 아직 미숙한 사람들에게 입문하기 좋은 프로그램이라고 생각하여 간단히 작성해 보았음.</p>
<p><img src="https://images.velog.io/images/aid_choi/post/166956fa-d620-41e1-918c-4eb63ab904b2/image.png" alt=""></p>
<p>GitHub Desktop 공식 홈페이지 주소 : <a href="https://desktop.github.com/">https://desktop.github.com/</a></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[Python3] 내가 까먹을까봐 끄적이는 백준 | 단어 수학 (아이디어)]]></title>
            <link>https://velog.io/@aid_choi/Python3-%EB%82%B4%EA%B0%80-%EA%B9%8C%EB%A8%B9%EC%9D%84%EA%B9%8C%EB%B4%90-%EB%81%84%EC%A0%81%EC%9D%B4%EB%8A%94-%EB%B0%B1%EC%A4%80-%EB%8B%A8%EC%96%B4-%EC%88%98%ED%95%99-%EC%95%84%EC%9D%B4%EB%94%94%EC%96%B4</link>
            <guid>https://velog.io/@aid_choi/Python3-%EB%82%B4%EA%B0%80-%EA%B9%8C%EB%A8%B9%EC%9D%84%EA%B9%8C%EB%B4%90-%EB%81%84%EC%A0%81%EC%9D%B4%EB%8A%94-%EB%B0%B1%EC%A4%80-%EB%8B%A8%EC%96%B4-%EC%88%98%ED%95%99-%EC%95%84%EC%9D%B4%EB%94%94%EC%96%B4</guid>
            <pubDate>Sat, 20 Nov 2021 17:44:53 GMT</pubDate>
            <description><![CDATA[<p><img src="https://images.velog.io/images/aid_choi/post/ec7f2ca0-31f0-45ca-a40d-4ce53703e975/image.png" alt="">
백준 1339번 단어수학!!</p>
<p><strong>&lt;문제&gt;</strong>, <strong>&lt;입력&gt;</strong>, <strong>&lt;출력&gt;</strong>을 게시글에 옮겨보면 다음과 같다</p>
<blockquote>
<h3 id="문제">문제</h3>
<p>민식이는 수학학원에서 단어 수학 문제를 푸는 숙제를 받았다.</p>
</blockquote>
<p>단어 수학 문제는 N개의 단어로 이루어져 있으며, 각 단어는 알파벳 대문자로만 이루어져 있다. 이때, 각 알파벳 대문자를 0부터 9까지의 숫자 중 하나로 바꿔서 N개의 수를 합하는 문제이다. 같은 알파벳은 같은 숫자로 바꿔야 하며, 두 개 이상의 알파벳이 같은 숫자로 바뀌어지면 안 된다.</p>
<blockquote>
</blockquote>
<p>예를 들어, GCF + ACDEB를 계산한다고 할 때, A = 9, B = 4, C = 8, D = 6, E = 5, F = 3, G = 7로 결정한다면, 두 수의 합은 99437이 되어서 최대가 될 것이다.</p>
<blockquote>
</blockquote>
<p>N개의 단어가 주어졌을 때, 그 수의 합을 최대로 만드는 프로그램을 작성하시오.</p>
<blockquote>
<h3 id="입력">입력</h3>
<p>첫째 줄에 단어의 개수 N(1 ≤ N ≤ 10)이 주어진다. 둘째 줄부터 N개의 줄에 단어가 한 줄에 하나씩 주어진다. 단어는 알파벳 대문자로만 이루어져있다. 모든 단어에 포함되어 있는 알파벳은 최대 10개이고, 수의 최대 길이는 8이다. 서로 다른 문자는 서로 다른 숫자를 나타낸다.</p>
</blockquote>
<blockquote>
<h3 id="출력">출력</h3>
<p>첫째 줄에 주어진 단어의 합의 최댓값을 출력한다.</p>
</blockquote>
<hr>
<h2 id="어떻게-접근해야-할까">어떻게 접근해야 할까?</h2>
<p>백준 문제들을 보면 항상 느끼는 것..!</p>
<p><strong>머리로는 모두 이해</strong>했지만 <strong>코드를 쓰려고 하면</strong> 막막하다는 것이다</p>
<p>사실 탐욕법 문제는 <strong>주어진 상황</strong>에서의 최적의 해를 구하는 알고리즘이기 때문에</p>
<p>다른 알고리즘에 비해서 문제가 단순하다고 한다 ( <del>물론 그래도 난 잘 못한다</del> )</p>
<h4 id="✏️-첫-접근">✏️ 첫 접근...!</h4>
<p>처음에는 더 자릿수가 큰 수의 알파벳에 큰 수를 부여하는 방법을 생각하였다.
하지만 얼마 지나지 않아 아래 같은 문제점을 발견할 수 있었다.</p>
<blockquote>
<h4 id="문제점">문제점</h4>
<p>ABC 1개와 BB 9개를 입력받은 경우를 생각해보자!</p>
</blockquote>
<p>A = 9, B = 8, C = 7 이라면 987 + 88 * 9 = 1,779</p>
<blockquote>
</blockquote>
<p>A = 8, B = 9, C = 7 이라면 897 + 99 * 9 = 1,788</p>
<blockquote>
</blockquote>
<p>더 긴 단어의 앞 자리 알파벳이 큰 경우가
<strong>반드시 최댓값을 도출하지는 않는다</strong>는 것을 알 수 있다!</p>
<p>그렇기 때문에 더 긴 단어의 앞 자리 알파벳에 초점을 맞춘다기 보다
우리가 구해야하는 결과값에 초점을 다시 맞춰 보았다.</p>
<h4 id="✏️-두-번째-접근">✏️ 두 번째 접근...!</h4>
<p>ABC와 EF가 주어졌다고 가정해보자
ABC + EF 를 수식으로 표현하면 다음과 같다</p>
<blockquote>
<p><em>(결과값)</em> = 100 * A + 10 * (B+C) + 1 (C+F)</p>
</blockquote>
<p>한 가지 경우만 더 표현해보자</p>
<p>ABB + AB 의 경우는 아래와 같다</p>
<blockquote>
<p><em>(결과값)</em> = 100 * A + 10 * (B+A) + 1 (2B)</p>
</blockquote>
<p>이 결과값을 A, B 따로 묶게 되면 다음과 같다.</p>
<blockquote>
<p><em>(결과값)</em> = 110 * A + 12 * B</p>
</blockquote>
<p>이로부터 착안한 아이디어는</p>
<p>A라는 Key를 만들어 110이라는 value를
B라는 Key를 만들어 12이라는 value를 할당한 뒤</p>
<p>value 값을 내림차순하여 순서대로
9.. 8.. 7.. 6.. . . . 과 같이 큰 수를 부여하는 것이다!</p>
<h3 id="완성된-코드">완성된 코드</h3>
<pre><code class="language-python">n = int(input())
answer = 0
saving = {}
values = []
num = 9

for _ in range(n):
    word = input()
    for s in range(len(word)):
        if word[s] in saving:
            saving[word[s]] += 10 ** (len(word) - 1 - s)
        else:
            saving[word[s]] = 10 ** (len(word) - 1 - s)

# print(saving)

for i in saving.values():
    values.append(i)

values.sort(reverse = True)

#print(values)

for j in values:
    answer += num * j
    num -= 1

print(answer)</code></pre>
<p>answer는 구하는 최종 답안
saving은** A : 111, B : 12 **처럼 각 알파벳의 가중치를 저장한 딕셔너리
values는 saving에서의 value 값들을 관리할 빈 리스트이다 !</p>
<pre><code>for _ in range(n):
    word = input()
    for s in range(len(word)):
        if word[s] in saving:
            saving[word[s]] += 10 ** (len(word) - 1 - s)
        else:
            saving[word[s]] = 10 ** (len(word) - 1 - s)
</code></pre><p>위 코드를 통해 알파벳이 처음 들어가는 경우에는
딕셔너리에 Key와 value를 해당 값으로 초기화해주며
알파벳이 딕셔너리에 존재하는 경우, 주어진 값에 더하도록 코드를 작성했다.</p>
<pre><code class="language-python">for i in saving.values():
    values.append(i)

values.sort(reverse = True)
</code></pre>
<p>saving의 저장된 value 값들을 빈 리스트 values에 저장한 뒤
.sort(reverse = True) 를 통해 내림차순으로 정렬해준다.</p>
<pre><code class="language-python">for j in values:
    answer += num * j
    num -= 1
</code></pre>
<p>values 에는 가중치가 가장 큰 순서부터 내림차순으로 정렬되어 있을테니
9부터 시작하여 차례대로 1씩 감소시켜 곱한 값을 answer에 더해준다.</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[Python3] 내가 까먹을까봐 끄적이는 백준 | 단어 수학 (에러 디버깅)]]></title>
            <link>https://velog.io/@aid_choi/Python3-%EB%82%B4%EA%B0%80-%EA%B9%8C%EB%A8%B9%EC%9D%84%EA%B9%8C%EB%B4%90-%EB%81%84%EC%A0%81%EC%9D%B4%EB%8A%94-%EB%B0%B1%EC%A4%80-%EB%8B%A8%EC%96%B4-%EC%88%98%ED%95%99-%EC%97%90%EB%9F%AC-%EB%94%94%EB%B2%84%EA%B9%85</link>
            <guid>https://velog.io/@aid_choi/Python3-%EB%82%B4%EA%B0%80-%EA%B9%8C%EB%A8%B9%EC%9D%84%EA%B9%8C%EB%B4%90-%EB%81%84%EC%A0%81%EC%9D%B4%EB%8A%94-%EB%B0%B1%EC%A4%80-%EB%8B%A8%EC%96%B4-%EC%88%98%ED%95%99-%EC%97%90%EB%9F%AC-%EB%94%94%EB%B2%84%EA%B9%85</guid>
            <pubDate>Sat, 20 Nov 2021 16:48:30 GMT</pubDate>
            <description><![CDATA[<p>11월에는 새로운 velog 시리즈 <strong>&lt;내가 까먹을까봐 끄적이는&gt;</strong>으로 돌아왔다.</p>
<p>개강하기 전, 방학 중에 알고리즘 문제를 간간히 풀면서 어느 정도 실력을 쌓았다고 생각하였지만</p>
<p>풀어본 문제들을 다시 살펴보면서 사용했던 아이디어나 오류 해결 방법이 잘 기억이 나지 않았다.</p>
<p>그래서 알고리즘 문제를 풀면서 사용한 아이디어나 디버깅 과정을 기록해보고자 한다.</p>
<hr>
<h2 id="💻-오늘-풀어볼-백준-문제는-">💻 오늘 풀어볼 백준 문제는 !!!</h2>
<p>백준 1339번 ( 단어 수학 )
<a href="http://www.acmicpc.net/problem/1339">www.acmicpc.net/problem/1339</a></p>
<hr>
<p>백준 1339번, 단어 수학 문제의 알고리즘 종류는 &#39;탐욕법(그리디)&#39;이다.</p>
<blockquote>
</blockquote>
<h2 id="탐욕법그리디란">탐욕법(그리디)란?</h2>
<p>탐욕법은 현재 상황에서 가장 좋은 것(최선의 상황)을 고르는 알고리즘을 의미한다.
그리디 알고리즘의 특징은 현재 상황에서는 가장 좋은 결과를 도출했음에도 그 결과가 최종적인 결과의 최적해라는 보장은 없다.</p>
<p><img src="https://images.velog.io/images/aid_choi/post/345a188b-08e6-4bb6-a1d0-8d6d141d46f0/image.png" alt="">
필자의 경우, 해당 문제를 처음 보고 아래와 같이 코드를 작성하였다.</p>
<pre><code class="language-python">n = int(input())
answer = 0
saving = {&#39;A&#39;:0, &#39;B&#39;:0, &#39;C&#39;:0, &#39;D&#39;:0, &#39;E&#39;:0, &#39;F&#39;:0, &#39;G&#39;:0, &#39;H&#39;:0, &#39;I&#39;:0, &#39;J&#39;:0}
values = []
num = 9

for _ in range(n):
    word = input()
    for s in range(len(word)):
        saving[word[s]] += 10 ** (len(word) - 1 - s)

# print(saving)

for i in saving.values():
    values.append(i)

values.sort(reverse = True)
# print(values)

for j in values:
    if j == 0:
        break
    else:
        answer += num * j
        num -= 1

print(answer)</code></pre>
<p>문제 내부에 있는 테스트 코드가 문제없이 통과되었기에 문제를 채점하였다..!</p>
<h3 id="하지만-결과는">하지만 결과는??</h3>
<p><img src="https://images.velog.io/images/aid_choi/post/4d9491a3-93bd-45af-9309-54687742a05d/image.png" alt=""></p>
<p>런타임 에러(KeyError)가 발생하였다!
구글링을 통해 알아보니 KeyError가 발생하는 경우는 딕셔너리에 해당하는 Key가 없을 때 접근하는 경우라고 한다.</p>
<p>처음 문제를 보고 알파벳의 최대 개수가 10개로 정해져 있기에 당연스럽게 입력값으로 주어지는 알파벳은 A부터 J까지라고 생각하였다.</p>
<p>하지만, 그렇지 않다면?</p>
<p>K~Z가 입력값으로 주어질 경우에는 <em>( 아래 코드를 보자! )</em></p>
<pre><code class="language-python">for _ in range(n):
    word = input()
    for s in range(len(word)):
        saving[word[s]] += 10 ** (len(word) - 1 - s)</code></pre>
<p>10 ** (len(word) - 1 - s) 값을 기존에 있는 Key의 value에 더해주는 과정을 수행할 수 없다는 것을 알았다.</p>
<hr>
<h3 id="다른-개선점은-없나">다른 개선점은 없나?</h3>
<p>주어지는 알파벳의 개수는 <strong>&#39;최대&#39; 10개</strong>인 것이지 모든 경우에서 10개를 다 쓰지 않는다!
하지만 처음 작성한 코드는 딕셔너리에서 알파벳 10개를 모두 관리하며, value 값들을 리스트에 저장할 때도 answer에 value 값들을 추가할 때도 불필요한 반복이 이루어진다는 것을 알았다.</p>
<hr>
<h2 id="keyerror와-불필요한-반복을-개선한-코드-">KeyError와 불필요한 반복을 개선한 코드 !</h2>
<pre><code class="language-python">n = int(input())
answer = 0
saving = {}
values = []
num = 9

for _ in range(n):
    word = input()
    for s in range(len(word)):
        if word[s] in saving:
            saving[word[s]] += 10 ** (len(word) - 1 - s)
        else:
            saving[word[s]] = 10 ** (len(word) - 1 - s)

# print(saving)

for i in saving.values():
    values.append(i)

values.sort(reverse = True)

#print(values)

for j in values:
    answer += num * j
    num -= 1

print(answer)</code></pre>
<p>word[s]가 saving이라는 딕셔너리에 존재하지 않는 경우에는 새로 추가해주고
존재하는 경우에는 value 값에 주어진 값들을 추가하는 방식으로 진행하였다.</p>
<p>또한, 이 과정에서 자연스럽게 사용되는 알파벳만 관리하기 때문에 answer에 값을 더하는 과정에서
이전 코드처럼 break를 통해 빈 value값을 갖는 경우를 따로 처리하지 않아도 된다!!</p>
<p><img src="https://images.velog.io/images/aid_choi/post/b44f5e71-abdd-4289-a3e1-2bb02e761991/image.png" alt=""></p>
<p>이 문제를 통해 어느 경우에 KeyError가 발생하는지, 파이썬에서 딕셔너리를 어떤 식으로 관리해주면 될 지에 대하여 알 수 있었다. 다음 포스팅은 &#39;단어 수학&#39;를 어떠한 아이디어를 통해 풀었는지 작성해볼 예정이다!</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[PyQt5] 계산기로 계산기 만들기(2)]]></title>
            <link>https://velog.io/@aid_choi/PyQt5-%EA%B3%84%EC%82%B0%EA%B8%B0%EB%A1%9C-%EA%B3%84%EC%82%B0%EA%B8%B0-%EB%A7%8C%EB%93%A4%EA%B8%B02</link>
            <guid>https://velog.io/@aid_choi/PyQt5-%EA%B3%84%EC%82%B0%EA%B8%B0%EB%A1%9C-%EA%B3%84%EC%82%B0%EA%B8%B0-%EB%A7%8C%EB%93%A4%EA%B8%B02</guid>
            <pubDate>Mon, 11 Oct 2021 20:35:02 GMT</pubDate>
            <description><![CDATA[<blockquote>
</blockquote>
<h1 id="to-do-list">To do List</h1>
<ul>
<li>버튼이 눌러지면 창에 입력되는 기능 구현하기</li>
<li>연산 기능 실행 버튼의 계산기능 구현 하기</li>
<li>전체 지우기 버튼의 지우기 기능 구현하기</li>
<li>UI 구성 코드의 개선</li>
</ul>
<p>이전 포스팅에서는 버튼 생성 함수를 간소화하였다.
이번에는 버튼이 눌러지면 창에 입력되는 기능을 구현할 것이다.</p>
<p>기존에 주어진 코드가 없기 때문에 바로 개선 코드로 넘어간다.</p>
<hr>
<h3 id="개선-코드_display에-입력할-수-있는-버튼들">개선 코드_display에 입력할 수 있는 버튼들</h3>
<pre><code class="language-python"># [0]~[9]까지는 차례대로 &#39;1&#39;, &#39;2&#39; . . . &#39;8&#39;, &#39;9&#39;에 해당한다.
self.digitButton[0].clicked.connect(lambda state, button=self.digitButton[0]: self.NumClicked(state, button))
self.digitButton[1].clicked.connect(lambda state, button=self.digitButton[1]: self.NumClicked(state, button))
self.digitButton[2].clicked.connect(lambda state, button=self.digitButton[2]: self.NumClicked(state, button))
self.digitButton[3].clicked.connect(lambda state, button=self.digitButton[3]: self.NumClicked(state, button))
self.digitButton[4].clicked.connect(lambda state, button=self.digitButton[4]: self.NumClicked(state, button))
self.digitButton[5].clicked.connect(lambda state, button=self.digitButton[5]: self.NumClicked(state, button))
self.digitButton[6].clicked.connect(lambda state, button=self.digitButton[6]: self.NumClicked(state, button))
self.digitButton[7].clicked.connect(lambda state, button=self.digitButton[7]: self.NumClicked(state, button))
self.digitButton[8].clicked.connect(lambda state, button=self.digitButton[8]: self.NumClicked(state, button))
self.digitButton[9].clicked.connect(lambda state, button=self.digitButton[9]: self.NumClicked(state, button))

# [0]~[7]까지는 차례대로 &#39;.&#39;, &#39;*&#39;, &#39;/&#39;, &#39;+&#39;, &#39;-&#39;, &#39;(&#39;, &#39;)&#39;에 해당한다.
self.signButton[0].clicked.connect(lambda state, button=self.signButton[0]: self.NumClicked(state, button))
self.signButton[2].clicked.connect(lambda state, button=self.signButton[2]: self.NumClicked(state, button))
self.signButton[3].clicked.connect(lambda state, button=self.signButton[3]: self.NumClicked(state, button))
self.signButton[4].clicked.connect(lambda state, button=self.signButton[4]: self.NumClicked(state, button))
self.signButton[5].clicked.connect(lambda state, button=self.signButton[5]: self.NumClicked(state, button))
self.signButton[6].clicked.connect(lambda state, button=self.signButton[6]: self.NumClicked(state, button))
self.signButton[7].clicked.connect(lambda state, button=self.signButton[7]: self.NumClicked(state, button))</code></pre>
<hr>
<p>계산기 UI에서 &#39;=&#39;나 &#39;C&#39; 버튼과 같이 결과값을 출력하는 버튼을 제외한 나머지 버튼들은 누름과 동시에 display에 해당 값들을 업데이트 해주어야 한다.
위에서 서술한 display에 값을 업데이트 해주는 함수를 NumClicked(self, state, button)로 만들어 각 버튼들을 클릭했을 때 연결되도록 코드를 작성해주었다.</p>
<hr>
<h3 id="numclickedself-state-button_초기-ver">NumClicked(self, state, button)_초기 ver</h3>
<pre><code class="language-python">def NumClicked(self, state, button):
        exist_line_text = self.display.text()
        now_num_text = button.text()
        self.display.setText(exist_line_text + now_num_text)
</code></pre>
<hr>
<p>작성한 코드를 간단히 설명해보자면 다음과 같다.</p>
<blockquote>
<ul>
<li>self.display.text()를 하여 display에 존재하는 텍스트를 변수 exist_line_text에 담는다.</li>
</ul>
</blockquote>
<ul>
<li>button.text()를 이용하여 버튼이 지칭하는 텍스트를 변수 now_num_text에 담는다.</li>
<li>위에서 저장한 두 변수를 이용하여 display에 새롭게 업데이트 시켜준다.</li>
</ul>
<p>머릿 속으로 생각한 알고리즘은 위와 같았고 별 문제없이 작동될 것이라고 생각하였으나 간과하고 있는 문제점이 하나 있었다.</p>
<p><img src="https://images.velog.io/images/aid_choi/post/a73d0b3a-5b8d-4293-bd1f-bedea2a534fe/0%EC%9D%B4%20%EB%AC%B8%EC%A0%9C%EC%95%BC.png" alt="">
계산기의 초기값이 &#39;0&#39;으로 설정이 되어있기 때문에 다른 버튼을 클릭하게 되면 앞에 &#39;0&#39;이 따라 붙게 되는 것이었다.
(ex: 초기 상태에서 7 입력시 사진과 같이 07이 display에 출력)</p>
<p>그래서 위 self.NumClicked(self, state, button) 함수를 아래와 같이 개선해보았다.</p>
<hr>
<h3 id="numclickedself-state-button_개선-ver">NumClicked(self, state, button)_개선 ver</h3>
<pre><code class="language-python">def NumClicked(self, state, button):
    exist_line_text = self.display.text()
    now_num_text = button.text()
    if exist_line_text == &#39;0&#39;: # 계산기의 초기값이 0이기 때문에 다뤄주어야 함
        if now_num_text == &#39;.&#39;: # 0 다음 소수점을 입력한 경우에는 0을 유지
            self.display.setText(exist_line_text + now_num_text)
        else: # 소수를 나타내지 않는 경우에는 초기값 0을 제거한 뒤, 입력한 값만 출력
            self.display.setText(now_num_text)
    else:
        self.display.setText(exist_line_text + now_num_text)</code></pre>
<hr>
<p>위와 같이 코드를 작성하게 될 경우, display에 &#39;0&#39;만 입력된 상태에서는 소수점(&#39;.&#39;)을 제외한 나머지 버튼을 누를 경우에는 now_num_text만 display에 업데이트하고 나머지 경우는 exist_line_text + now_num_text를 업데이트 하도록 했다.</p>
<hr>
<h3 id="makeresultself">MakeResult(self)</h3>
<pre><code class="language-python">def MakeResult(self):
    result = eval(self.display.text()) # 이때 result의 자료형은 int
        # self.display.setText(result) &lt;- TypeError: setText(self, str): argument 1 has unexpected type &#39;int&#39;
    self.display.setText(str(result))</code></pre>
<p>다음으로는 &#39;=&#39; 버튼을 눌렀을 경우에 display에 담긴 수식을 계산해주는 함수 MakeResult(self)를 만들었다.</p>
<p>위에서 사용한 eval 함수이 핵심이기에 보충 설명을 하면 다음과 같다.</p>
<blockquote>
</blockquote>
<h3 id="eval">eval()</h3>
<ul>
<li>매개변수를 문자열로 받아서 실행하는 함수</li>
<li>이때 매개변수로 받은 문자열은 파이썬이 실행 가능한 문자열이 들어와야함 (주의점)</li>
</ul>
<p>eval()을 사용하여 나온 결과의 타입은 String이 아니기 때문에 display에 업데이트 하기 전 String으로 타입을 변환시켜야만 정상적으로 코드가 작동됨을 추가로 확인할 수 있었다.
<img src="https://images.velog.io/images/aid_choi/post/39663c6c-2178-424f-b10f-b445eb31ca30/%EA%B3%84%EC%82%B0%EA%B8%B0%20%EA%B2%B0%EA%B3%BC.png" alt=""></p>
<hr>
<p>마지막으로 &#39;C&#39; 버튼을 눌렀을 경우에 display의 text를 초기값인 &#39;0&#39;으로 변경해주는 함수 RemoveAll(self)를 만들었다. </p>
<h3 id="removeallself">RemoveAll(self)</h3>
<pre><code class="language-python">def RemoveAll(self):
    self.display.setText(&#39;0&#39;)</code></pre>
<p>너무나도 직관적인 코드여서 마음에 쏙 들었던 코드다.</p>
<hr>
<p>MakeResult(self)와 RemoveAll(self) 함수는 각각 &#39;=&#39; 버튼과 &#39;C&#39; 버튼을 눌렀을 때 작동되어야 한다. 따라서 아래 코드를 이용하여 위 코드들과는 독립적으로 함수에 연결되도록 설정해야 한다.</p>
<h3 id="-버튼과-c버튼-함수와-연결">&#39;=&#39; 버튼과 &#39;C&#39;버튼 함수와 연결</h3>
<pre><code class="language-python">self.signButton[8].clicked.connect(self.RemoveAll) 
# self.signButton[8]은 &#39;C&#39;(Clear_모든 계산 데이터 삭제) 명령어여서 따로 분리함.

self.signButton[1].clicked.connect(self.MakeResult) 
# self.signButton[1]은 &#39;=&#39; 명령어여서 따로 분리함.</code></pre>
<hr>
<p>이로써 기능적인 측면은 현재 모두 구현이 완료된 상태이다.</p>
<p>앞으로 &#39;멍청이 계산기 만들기&#39; 프로젝트는 두 차례 정도에 걸쳐 보완을 할 예정인데 다음과 같다.</p>
<blockquote>
</blockquote>
<ul>
<li>반복되는 코드 간소화</li>
<li>치명적이지는 않지만 거슬리는 자잘한 에러 디버깅</li>
</ul>
<p>아무런 것도 하지 못하던 내 계산기가 점점 제 구실을 할 수 있게 되니 조금씩 흥미가 붙는다.</p>
<p>처음부터 완벽하게 코드를 짜는 것도 중요하지만 스스로 짠 코드를 여러 테스트 케이스를 만들고 실행시켜보는 것 또한 중요하다는 것을 몸소 느끼게 되는 소규모 과제인 것 같다.</p>
<blockquote>
<p>우리 계산기, 형이 힘내고 있는 거 조금 알아줬으면 좋겠다... </p>
</blockquote>
]]></description>
        </item>
        <item>
            <title><![CDATA[[PyQt5] 계산기로 계산기 만들기(1)]]></title>
            <link>https://velog.io/@aid_choi/PyQt5-%EA%B3%84%EC%82%B0%EA%B8%B0%EB%A1%9C-%EA%B3%84%EC%82%B0%EA%B8%B0-%EB%A7%8C%EB%93%A4%EA%B8%B0</link>
            <guid>https://velog.io/@aid_choi/PyQt5-%EA%B3%84%EC%82%B0%EA%B8%B0%EB%A1%9C-%EA%B3%84%EC%82%B0%EA%B8%B0-%EB%A7%8C%EB%93%A4%EA%B8%B0</guid>
            <pubDate>Mon, 11 Oct 2021 18:44:33 GMT</pubDate>
            <description><![CDATA[<p><img src="https://images.velog.io/images/aid_choi/post/10350be9-5a34-4baf-87fd-05843cce0db4/%EB%B8%94%EB%A1%9C%EA%B7%B8%201.png" alt="">
2021년 10월 11일, 한글날 대체공휴일을 맞이하여 새로운 과제가 등록되었다.
과제는 Python3, PyQt5를 이용하여 계산기 구현하기!</p>
<p>컴퓨터라는 똑똑이 계산기로 기능도 몇 없는 멍충이 계산기를 만들 생각을 하니 벌써부터 설렌다.</p>
<p><img src="https://images.velog.io/images/aid_choi/post/e787168d-581b-41a0-9060-b65c39b70ef6/%EA%B3%84%EC%82%B0%EA%B8%B0.png" alt="">
기본적으로 주어진 .py 파일에는 계산기의 기본 레이아웃이 완성되어 있었다.</p>
<blockquote>
</blockquote>
<h1 id="to-do-list">To do List</h1>
<ul>
<li>버튼이 눌러지면 창에 입력되는 기능 구현하기</li>
<li>연산 기능 실행 버튼의 계산기능 구현 하기</li>
<li>전체 지우기 버튼의 지우기 기능 구현하기</li>
<li>UI 구성 코드의 개선</li>
</ul>
<p>그 중에서도 4번째 &quot;UI 구성 코드의 개선&quot;에서 버튼 생성 코드 반복 줄이기를 첫 번째 목표로 잡았다.</p>
<hr>
<h3 id="기존-코드">기존 코드</h3>
<pre><code class="language-python"># Digit Buttons

self.digitButton[0] = Button(&#39;0&#39;)
self.digitButton[1] = Button(&#39;1&#39;)
self.digitButton[2] = Button(&#39;2&#39;)
self.digitButton[3] = Button(&#39;3&#39;)
self.digitButton[4] = Button(&#39;4&#39;)
self.digitButton[5] = Button(&#39;5&#39;)
self.digitButton[6] = Button(&#39;6&#39;)
self.digitButton[7] = Button(&#39;7&#39;)
self.digitButton[8] = Button(&#39;8&#39;)
self.digitButton[9] = Button(&#39;9&#39;)

# . and = Buttons
self.decButton = Button(&#39;.&#39;)
self.eqButton = Button(&#39;=&#39;)

# Operator Buttons
self.mulButton = Button(&#39;*&#39;)
self.divButton = Button(&#39;/&#39;)
self.addButton = Button(&#39;+&#39;)
self.subButton = Button(&#39;-&#39;)

# Parentheses Buttons
self.lparButton = Button(&#39;(&#39;)
self.rparButton = Button(&#39;)&#39;)

# Clear Button
self.clearButton = Button(&#39;C&#39;)</code></pre>
<hr>
<h3 id="개선-코드">개선 코드</h3>
<pre><code class="language-python"># Digit Buttons
self.digitButton = [x for x in range(0, 10)]

for i in range(10):  # for문을 이용하여 Digit Buttons 생성코드 축약
    str_i = str(i)
    self.digitButton[i] = Button(str_i)

# Sign Buttons
signs = [&#39;.&#39;, &#39;=&#39;, &#39;*&#39;, &#39;/&#39;, &#39;+&#39;, &#39;-&#39;, &#39;(&#39;, &#39;)&#39;, &#39;C&#39;]
self.signButton = [x for x in range(0, 9)]

for j in range(9):
    self.signButton[j] = Button(signs[j])
</code></pre>
<hr>
<p>계산기에서 숫자(0~9)를 입력하는 버튼은 &#39;Digit Buttons&#39;로 묶은 뒤, 기본 파일에서 주어진 &#39;. and = Buttons&#39;, &#39;Operator Buttons&#39;, &#39;Parenthese Buttons&#39;, &#39;Clear Button&#39;들을 Sign Buttons이라는 하나의 묶음으로 다시 바꿔주었다.</p>
<p>필요한 버튼의 개수를 고려하여 빈 리스트를 만들어준 뒤, for문과 sings라는 리스트를 이용하여 전체적인 코드의 줄 수를 줄여주었다.</p>
<p>하지만 이전 코드와 달리 각 버튼이 수행하는 기능이 명확하게 구별되지 않기 때문에 아래에 주석을 추가로 다는 것으로 이를 보완하였다.</p>
<hr>
<h3 id="주석-예시_일부">주석 예시_일부</h3>
<pre><code class="language-python">numLayout.addWidget(self.signButton[0], 3, 1) # decButton (&#39;.&#39;)
numLayout.addWidget(self.signButton[1], 3, 2) # eqButton (&#39;=&#39;)
</code></pre>
<hr>
<p>이것으로 버튼 생성 코드의 반복을 간소화시켰으니 다음은 버튼이 눌러지면 창에 입력되는 기능을 구현해보려고 한다 :)</p>
]]></description>
        </item>
    </channel>
</rss>