<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
    <channel>
        <title>devel_liz.log</title>
        <link>https://velog.io/</link>
        <description>Android zizon</description>
        <lastBuildDate>Thu, 16 Jan 2025 06:31:17 GMT</lastBuildDate>
        <docs>https://validator.w3.org/feed/docs/rss2.html</docs>
        <generator>https://github.com/jpmonette/feed</generator>
        <image>
            <title>devel_liz.log</title>
            <url>https://velog.velcdn.com/images/devel_liz/profile/293d0cdf-7c90-4033-9d5e-a7d42bb89fc6/image.webp</url>
            <link>https://velog.io/</link>
        </image>
        <copyright>Copyright (C) 2019. devel_liz.log. All rights reserved.</copyright>
        <atom:link href="https://v2.velog.io/rss/devel_liz" rel="self" type="application/rss+xml"/>
        <item>
            <title><![CDATA[velog 거진 두 달 사용 후기]]></title>
            <link>https://velog.io/@devel_liz/velog-%EA%B1%B0%EC%A7%84-%EB%91%90-%EB%8B%AC-%EC%82%AC%EC%9A%A9-%ED%9B%84%EA%B8%B0-99sa4m7u</link>
            <guid>https://velog.io/@devel_liz/velog-%EA%B1%B0%EC%A7%84-%EB%91%90-%EB%8B%AC-%EC%82%AC%EC%9A%A9-%ED%9B%84%EA%B8%B0-99sa4m7u</guid>
            <pubDate>Thu, 16 Jan 2025 06:31:17 GMT</pubDate>
            <description><![CDATA[<h3 id="결론부터-말씀드리자면-다시-티스토리로-돌아가고자-한다">결론부터 말씀드리자면 다시 티스토리로 돌아가고자 한다..</h3>
<p>깔끔한 UI와 태그로 카테고리를 나눠주는 기능, 부제목에 따라 오른쪽에 목차가 자동 생성되는 이점 때문에 사용했지만 velog 처음 진입 시 로딩이 너무 길다. 왜? 인지는 모르겠으나 이외에도 글을 장시간 작성할 경우 작성하기 버튼을 누르면 화면이 움직임 없이 그대로 멈춰 있고 시리즈 추가한 상태에서 작성하기를 여러번 누르면 글은 1개인데 시리즈 목록에는 2개가 생성된다.</p>
<p>위와 같은 이유로 자잘한 스트레스를 받고 있다가 결국 더는 못 쓸 것 같는 결론에 도달했다 😂</p>
<p><em>velog 접속하면 간헐적으로 일어났던 로딩 문제 이미지 첨부합니다.</em>
<img src="https://velog.velcdn.com/images/devel_liz/post/8421987e-e08c-4b53-8722-e7255d2a57f5/image.gif" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/87574904-8d3c-45d1-bcee-f59d1a529c5b/image.jpg" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/304097ba-fba3-4f13-8123-f0aec8e400fb/image.jpg" alt=""></p>
<p>velog 그동안 고마웠다.. 잘 가라 🤚🏻🤚🏻
나머지 글은 다시 티스토리에 이어서 작성하도록 하겠습니다.</p>
<p>티스토리에서 만나요! 😘
<a href="https://jokerapp.tistory.com/">https://jokerapp.tistory.com/</a></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 왼쪽 오른쪽]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%99%BC%EC%AA%BD-%EC%98%A4%EB%A5%B8%EC%AA%BD-2m05fhax</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%99%BC%EC%AA%BD-%EC%98%A4%EB%A5%B8%EC%AA%BD-2m05fhax</guid>
            <pubDate>Thu, 16 Jan 2025 03:47:42 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/f7dbc7fc-38ec-4916-9584-7d46257ce66f/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(strList: Array&lt;String&gt;): Array&lt;String&gt; {
        // &quot;l&quot;과 &quot;r&quot;의 인덱스를 찾음
        val lIndex = strList.indexOf(&quot;l&quot;)
        val rIndex = strList.indexOf(&quot;r&quot;)

        // &quot;l&quot;과 &quot;r&quot; 중 먼저 나오는 문자열에 따라 결과 반환
        return when {
            lIndex in strList.indices &amp;&amp; (rIndex !in strList.indices || lIndex &lt; rIndex) -&gt; {
                strList.copyOfRange(0, lIndex)
            }
            rIndex in strList.indices -&gt; {
                strList.copyOfRange(rIndex + 1, strList.size)
            }
            else -&gt; {
                arrayOf() // &quot;l&quot;과 &quot;r&quot;이 모두 없는 경우 빈 배열 반환
            }
        }
    }
}
</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(strList: Array&lt;String&gt;): Array&lt;String&gt; {
        if (!strList.contains(&quot;r&quot;) &amp;&amp; !strList.contains(&quot;l&quot;)) return emptyArray()
        if (strList.contains(&quot;l&quot;) &amp;&amp; (!strList.contains(&quot;r&quot;) || strList.indexOf(&quot;l&quot;) &lt; strList.indexOf(&quot;r&quot;))) return strList.sliceArray(0 until strList.indexOf(&quot;l&quot;))
        if (strList.contains(&quot;r&quot;) &amp;&amp; (!strList.contains(&quot;l&quot;) || strList.indexOf(&quot;r&quot;) &lt; strList.indexOf(&quot;l&quot;))) return strList.sliceArray((strList.indexOf(&quot;r&quot;) + 1) until strList.size)
        return emptyArray()
    }
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li><p>indexOf</p>
<ul>
<li>특정 요소가 배열에 존재하면 해당 요소의 첫 번째 인덱스를 반환.</li>
<li>요소가 없으면 -1 반환.<pre><code class="language-kotlin">val index = arrayOf(&quot;a&quot;, &quot;b&quot;, &quot;c&quot;).indexOf(&quot;b&quot;) // 결과: 1
val notFound = arrayOf(&quot;a&quot;, &quot;b&quot;, &quot;c&quot;).indexOf(&quot;d&quot;) // 결과: -1</code></pre>
</li>
</ul>
</li>
<li><p>contains</p>
<ul>
<li>배열에 특정 요소가 포함되어 있는지 확인.</li>
<li>반환값: true 또는 false.<pre><code class="language-kotlin">val hasElement = arrayOf(&quot;a&quot;, &quot;b&quot;, &quot;c&quot;).contains(&quot;b&quot;) // 결과: true
val notFound = arrayOf(&quot;a&quot;, &quot;b&quot;, &quot;c&quot;).contains(&quot;d&quot;) // 결과: false</code></pre>
</li>
</ul>
</li>
<li><p>when 표현식</p>
<ul>
<li>여러 조건을 분기 처리할 때 간결하고 읽기 좋은 구문.</li>
<li>조건문 대신 사용 가능.<pre><code class="language-kotlin">val x = 10
val result = when {
x &gt; 5 -&gt; &quot;Greater than 5&quot;
x == 5 -&gt; &quot;Equal to 5&quot;
else -&gt; &quot;Less than 5&quot;
}

</code></pre>
</li>
</ul>
</li>
</ul>
<ul>
<li><p>emptyArray</p>
<ul>
<li>빈 배열 생성 시 사용.</li>
<li>배열에 아무것도 반환할 필요가 없을 때 유용.<pre><code class="language-kotlin">val empty = emptyArray&lt;String&gt;() // 결과: []</code></pre>
</li>
</ul>
</li>
<li><p>sliceArray</p>
<ul>
<li>배열의 특정 범위를 추출하여 새로운 배열을 반환합니다.</li>
<li>범위는 IntRange 또는 until 키워드로 지정.</li>
<li>인덱스 포함 여부:<ul>
<li>시작 인덱스는 포함.</li>
<li>끝 인덱스는 포함.<pre><code class="language-kotlin">val array = arrayOf(&quot;a&quot;, &quot;b&quot;, &quot;c&quot;, &quot;d&quot;)
val result = array.sliceArray(0..2) // [&quot;a&quot;, &quot;b&quot;, &quot;c&quot;] (인덱스 0, 1, 2 포함)
val result2 = array.sliceArray(1 until 3) // [&quot;b&quot;, &quot;c&quot;] (인덱스 1, 2 포함)</code></pre>
</li>
</ul>
</li>
</ul>
</li>
<li><p>copyOfRange </p>
<ul>
<li>배열의 시작 인덱스와 끝 인덱스를 지정하여 새로운 배열을 반환합니다.</li>
<li>인덱스 포함 여부:<ul>
<li>시작 인덱스는 포함.</li>
<li>끝 인덱스는 포함되지 않음.<pre><code class="language-kotlin">val array = arrayOf(&quot;a&quot;, &quot;b&quot;, &quot;c&quot;, &quot;d&quot;)
val result = array.copyOfRange(0, 3) // [&quot;a&quot;, &quot;b&quot;, &quot;c&quot;] (인덱스 0, 1, 2 포함, 3은 제외)
val result2 = array.copyOfRange(1, 3) // [&quot;b&quot;, &quot;c&quot;] (인덱스 1, 2 포함, 3은 제외)

</code></pre>
</li>
</ul>
</li>
</ul>
</li>
</ul>
<h4 id="slicearray-vs-copyofrange">sliceArray vs copyOfRange</h4>
<table>
<thead>
<tr>
<th><strong>특징</strong></th>
<th><strong>sliceArray</strong></th>
<th><strong>copyOfRange</strong></th>
</tr>
</thead>
<tbody><tr>
<td><strong>범위 지정 방식</strong></td>
<td><code>IntRange</code> 또는 <code>until</code> 사용</td>
<td>시작 인덱스와 끝 인덱스 명시</td>
</tr>
<tr>
<td><strong>시작 인덱스 포함</strong></td>
<td>포함</td>
<td>포함</td>
</tr>
<tr>
<td><strong>끝 인덱스 포함</strong></td>
<td>포함</td>
<td>포함되지 않음</td>
</tr>
<tr>
<td><strong>반환 타입</strong></td>
<td>원본 배열과 동일한 타입의 배열 반환</td>
<td>원본 배열과 동일한 타입의 배열 반환</td>
</tr>
<tr>
<td><strong>예제 결과</strong></td>
<td><code>sliceArray(0..2)</code> -&gt; <code>[&quot;a&quot;, &quot;b&quot;, &quot;c&quot;]</code></td>
<td><code>copyOfRange(0, 3)</code> -&gt; <code>[&quot;a&quot;, &quot;b&quot;, &quot;c&quot;]</code></td>
</tr>
</tbody></table>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 순서 바꾸기]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%88%9C%EC%84%9C-%EB%B0%94%EA%BE%B8%EA%B8%B0</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%88%9C%EC%84%9C-%EB%B0%94%EA%BE%B8%EA%B8%B0</guid>
            <pubDate>Thu, 16 Jan 2025 01:34:17 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/148e4307-eb98-498b-a61d-0545902bf201/image.png" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/3ffc56fc-a3ce-4ad4-a9f3-1d5b20eef968/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(numList: IntArray, n: Int): IntArray {
         val aList = numList.copyOfRange(n, numList.size)
         val bList = numList.copyOfRange(0, n)
         return aList + bList
    }
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(numList: IntArray, n: Int) = (numList + numList).copyOfRange(n, n + numList.size)
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li>copyOfRange<ul>
<li>배열의 특정 범위를 복사해 새로운 배열을 반환.</li>
<li>포함 여부: 시작 인덱스는 포함, 끝 인덱스는 제외.<pre><code class="language-kotlin">val array = intArrayOf(1, 2, 3, 4, 5)
val subArray = array.copyOfRange(1, 4) // 1번부터 3번까지 복사
println(subArray.joinToString()) // 출력: 2, 3, 4

</code></pre>
</li>
</ul>
</li>
</ul>
<ul>
<li>효율적인 배열 회전 (다른 사람의 풀이)<ul>
<li>(numList + numList)로 배열을 두 번 이어 붙여 하나의 큰 배열 생성.</li>
<li>필요한 범위만 copyOfRange로 잘라서 반환.</li>
<li>메모리 효율적이며, 코드가 간결해짐.<pre><code class="language-kotlin">val numList = intArrayOf(1, 2, 3, 4, 5)
val rotated = (numList + numList).copyOfRange(2, 7)
println(rotated.joinToString()) // 출력: 3, 4, 5, 1, 2
</code></pre>
</li>
</ul>
</li>
</ul>
<p>```</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] n 번째 원소부터]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-n-%EB%B2%88%EC%A7%B8-%EC%9B%90%EC%86%8C%EB%B6%80%ED%84%B0-efyvdhgc</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-n-%EB%B2%88%EC%A7%B8-%EC%9B%90%EC%86%8C%EB%B6%80%ED%84%B0-efyvdhgc</guid>
            <pubDate>Thu, 16 Jan 2025 01:06:37 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/719d4b9b-fa80-44f1-b284-d1bdd1fb1b52/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(num_list: IntArray, n: Int): IntArray {
       return if(n-1 == num_list.size){
            intArrayOf(num_list[n-1])
    }else{
            num_list.sliceArray((n-1)..(num_list.size-1))
        }
    }
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(numList: IntArray, n: Int) = numList.copyOfRange(n - 1, numList.size)
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li>sliceArray<ul>
<li>sliceArray는 범위의 시작 인덱스와 끝 인덱스를 모두 포함한다</li>
<li>반환 타입: 호출한 배열과 같은 타입의 배열을 반환합니다.<pre><code class="language-kotlin">val array = intArrayOf(1, 2, 3, 4, 5)
val sliced = array.sliceArray(1..3)
println(sliced.joinToString()) // 출력: 2, 3, 4</code></pre>
</li>
</ul>
</li>
<li>copyOfRange<ul>
<li>배열의 특정 범위의 요소들을 복사해 새로운 배열을 반환.</li>
<li>끝값은 포함되지 않음 (startIndex부터 endIndex - 1까지).<pre><code class="language-kotlin">val array = intArrayOf(1, 2, 3, 4, 5)
val copied = array.copyOfRange(1, 4)
println(copied.joinToString()) // 출력: 2, 3, 4</code></pre>
</li>
</ul>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 배열 조각하기]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%B0%B0%EC%97%B4-%EC%A1%B0%EA%B0%81%ED%95%98%EA%B8%B0</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%B0%B0%EC%97%B4-%EC%A1%B0%EA%B0%81%ED%95%98%EA%B8%B0</guid>
            <pubDate>Wed, 15 Jan 2025 09:31:51 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/eadc3172-3fb5-463e-808f-fe552427b7a0/image.png" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/9c95a126-11b8-4803-b29c-8c392c53cf8c/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(arr: IntArray, query: IntArray): IntArray {
        var tempArr = arr 
        query.forEachIndexed{idx, value -&gt; 
            tempArr = if(idx % 2 ==0){
            tempArr.take(value + 1).toIntArray()
        }else{
            tempArr.drop(value).toIntArray()
            }
        }
        return tempArr
    }
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(arr: IntArray, query: IntArray) = query.indices
        .fold(0 to 0) { (s, e), i -&gt; if (i % 2 == 1) s + query[i] to e else s to s + query[i] }
        .let { (s, e) -&gt; if (s == e) intArrayOf(-1) else arr.copyOfRange(s, e) }
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li><p>take(n)</p>
<ul>
<li>배열 또는 리스트에서 앞에서부터 n개의 요소를 가져옴.</li>
<li>반환 타입: List<T><pre><code class="language-kotlin">val arr = listOf(1, 2, 3, 4, 5)
println(arr.take(3)) // [1, 2, 3]</code></pre>
</li>
</ul>
</li>
<li><p>drop(n)</p>
<ul>
<li>배열 또는 리스트에서 앞에서부터 n개의 요소를 제외한 나머지를 반환.</li>
<li>반환 타입: List<T><pre><code class="language-kotlin">val arr = listOf(1, 2, 3, 4, 5)
println(arr.drop(2)) // [3, 4, 5]</code></pre>
</li>
</ul>
</li>
<li><p>fold(initial, operation)</p>
<ul>
<li>컬렉션을 순회하며 누적 작업을 수행.</li>
<li>반환 타입: 누적 작업 결과 타입.<pre><code class="language-kotlin">val result = listOf(1, 2, 3).fold(0) { acc, value -&gt; acc + value }
println(result) // 6</code></pre>
</li>
</ul>
</li>
<li><p>copyOfRange(startIndex, endIndex)</p>
<ul>
<li>배열에서 startIndex부터 endIndex 직전까지의 요소를 복사.</li>
<li>반환 타입: 배열과 동일한 타입</li>
</ul>
<pre><code class="language-kotlin">val arr = intArrayOf(1, 2, 3, 4, 5)
 val subArray = arr.copyOfRange(1, 4)
  println(subArray.joinToString()) // 2, 3, 4

- indices
  - 배열이나 리스트의 모든 인덱스 범위를 반환.
  - 반환 타입: IntRange
```kotlin
   val arr = listOf(10, 20, 30)
   println(arr.indices) // 0..2</code></pre>
</li>
<li><p>let</p>
<ul>
<li>객체를 변환하거나 실행 블록을 전달받아 결과를 반환.</li>
<li>반환 타입: 블록의 결과값<pre><code class="language-kotlin">val result = listOf(1, 2, 3).let { it.sum() }
println(result) // 6</code></pre>
</li>
</ul>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 배열 만들기 3]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%B0%B0%EC%97%B4-%EB%A7%8C%EB%93%A4%EA%B8%B0-3</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%B0%B0%EC%97%B4-%EB%A7%8C%EB%93%A4%EA%B8%B0-3</guid>
            <pubDate>Wed, 15 Jan 2025 05:57:20 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/95968294-92bd-449d-8944-5756e5876934/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(arr: IntArray, intervals: Array&lt;IntArray&gt;): IntArray {
     val result = mutableListOf&lt;Int&gt;()
        for ((first, second) in intervals) {
            result.addAll(arr.sliceArray(first..second).toList()) 
        }
        return result.toIntArray()
    }
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(arr: IntArray, intervals: Array&lt;IntArray&gt;): List&lt;Int&gt; {
        return intervals.flatMap { ints -&gt; arr.sliceArray(IntRange(ints[0], ints[1])).toList() }
    }
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li><p>flatMap</p>
<ul>
<li>flatMap은 컬렉션의 각 요소를 처리한 결과를 하나의 리스트로 합쳐주는 함수입니다. 각 요소에 대해 매핑된 결과를 평평하게(flatten) 만들어 줍니다.<pre><code class="language-kotlin">val nestedList = listOf(listOf(1, 2), listOf(3, 4))
val flatList = nestedList.flatMap { it }
println(flatList) // 출력: [1, 2, 3, 4]</code></pre>
</li>
</ul>
</li>
<li><p>sliceArray</p>
<ul>
<li>sliceArray는 주어진 인덱스 범위나 인덱스 리스트에 해당하는 배열의 부분 <strong>배열을 반환</strong>합니다.<pre><code class="language-kotlin">val arr = intArrayOf(1, 2, 3, 4, 5)
val sliced = arr.sliceArray(1..3) // [2, 3, 4]
println(sliced.joinToString()) // 출력: 2, 3, 4</code></pre>
</li>
</ul>
</li>
<li><p>IntRange(start, endInclusive)</p>
<ul>
<li>ntRange는 정수 범위를 표현하는 클래스입니다. start..end와 같이 범위를 생성하며, step 값을 추가해 범위를 커스터마이즈할 수도 있습니다.</li>
<li>포함 범위: IntRange는 start부터 endInclusive까지 포함합니다. 즉, 끝값(endInclusive)도 범위에 포함됩니다.</li>
<li>표현식: 1..5는 IntRange(1, 5)와 동일한 표현입니다</li>
<li>사용 용도: 배열이나 리스트의 일부를 처리하거나 루프 범위를 지정할 때 자주 사용됩니다.</li>
</ul>
<pre><code class="language-kotlin">val range = IntRange(1, 5)
println(range.toList()) // 출력: [1, 2, 3, 4, 5]

for (i in IntRange(3, 7)) {
  println(i) // 출력: 3, 4, 5, 6, 7
}
</code></pre>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[Serializable과 Parcelable의 직렬화/역직렬화 방식에 대해..]]></title>
            <link>https://velog.io/@devel_liz/Serializable%EA%B3%BC-Parcelable%EC%9D%98-%EC%A7%81%EB%A0%AC%ED%99%94%EC%97%AD%EC%A7%81%EB%A0%AC%ED%99%94-%EB%B0%A9%EC%8B%9D%EC%97%90-%EB%8C%80%ED%95%B4</link>
            <guid>https://velog.io/@devel_liz/Serializable%EA%B3%BC-Parcelable%EC%9D%98-%EC%A7%81%EB%A0%AC%ED%99%94%EC%97%AD%EC%A7%81%EB%A0%AC%ED%99%94-%EB%B0%A9%EC%8B%9D%EC%97%90-%EB%8C%80%ED%95%B4</guid>
            <pubDate>Sun, 05 Jan 2025 10:03:31 GMT</pubDate>
            <description><![CDATA[<p>일단 내가 이 포스팅을 쓴 이유는 이번에 플젝을 하면서 @SerializedName과 @Parcelize를 같이 쓴 코드가 있고 이렇게 써도 아무 문제가 없는지 궁금해져서 작성하게 된 포스팅입니도 🙏</p>
<p>내가 작성한 코드</p>
<pre><code class="language-kotlin">@Parcelize
data class RouteResponse(
    @SerializedName(&quot;features&quot;)
    val features: List&lt;FeatureEntity&gt;
) : Parcelable</code></pre>
<p>왜 위처럼 썼냐면</p>
<ol>
<li>해당 데이터를 bundle로 주고받을 일이 있어서 <code>Parcelable</code>과 <code>@Parcelize</code>를 사용함</li>
<li>RouteResponse를 API 통신을 통해 받아오고 있기 때문에 프로퍼티 매핑을 위하여 <code>@SerializedName(&quot;features&quot;)</code>을 사용함</li>
</ol>
<p>결론: 찾아본 결과 함께 사용하는 것은 문제가 없다. 두 어노테이션은 서로 다른 용도로 사용되며 위 코드처럼 사용할 경우 각자 역할을 잘 수행할 수 있다.</p>
<p>그래도 이번 기회에 한번 더 직렬화/역직렬화에 대해 공부해보기로 함
<img src="https://velog.velcdn.com/images/devel_liz/post/ed76b5f2-8774-4daa-85a1-c7b0a17c0dbf/image.png" alt=""></p>
<hr>
<h2 id="serializable에-대해-알아보자">Serializable에 대해 알아보자!</h2>
<p>Serializable은 <strong>&quot;직렬화 가능&quot;</strong>이란 뜻이고 <strong>&quot;시리얼라이져블&quot;</strong>이라고 발음한다.</p>
<h3 id="직렬화-그게-뭔데">직렬화? 그게 뭔데.</h3>
<p>데이터를 주고 받거나 저장할 때 일정한 형식으로 바꾸는 것을 뜻한다.</p>
<p><em>그러니까 어떤 것을 어떤 것으로 바꾼다는 건데...</em></p>
<p>자바에서 뜻하는 직렬화로 말하자면 객체를 바이트 스트림으로 변환하여 파일로 저장하거나 네트워크를 통해 전송할 수 있게 만드는 과정이다.
반대로, 바이트 스트림을 객체로 복원하는 &quot;역직렬화&quot; 라고 해!
<img src="https://velog.velcdn.com/images/devel_liz/post/933af1d8-1ee1-46e8-b7e5-ebd6492d8de8/image.png" alt=""></p>
<h6 id="사진-출처-httpswwwgeeksforgeeksorgserialization-in-java">(사진 출처 <a href="https://www.geeksforgeeks.org/serialization-in-java/">https://www.geeksforgeeks.org/serialization-in-java/</a>)</h6>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/d8b64cda-6933-4bc7-8a9d-34cf82351572/image.png" alt=""></p>
<h3 id="왜-직렬화가-필요할까">왜 직렬화가 필요할까?</h3>
<p>&quot;바이트스트림이고 뭐고 그냥 저장하면 되는 거 아니야?&quot;
&quot;왜 꼭 변환해서 저장해야 돼?&quot;
&quot;왜 꼭 변환해서 데이터를 주고받아야 해?&quot;</p>
<p>라고 생각할 수 있다.</p>
<p>그 이유는 우선 바이트 스트림은 어떠한 플랫폼에도 종속되지 않는다.
윈도우, 리눅스, 맥 등 서로 다른 환경에서도 같은 데이터를 해석할 수 있고
바이트 스트림은 저장 공간을 최소화하여 읽기/쓰기에도 빠르다!
또한 객체 구조 유지도 해준다. 속성 값, 참조 관계 등을 그대로 저장해준다.
네트워크로 데이터를 전송할 때는 표준적으로 바이트 단위를 사용하기 때문에 네트워크 통신도 수월해진다.</p>
<h3 id="어떻게-사용하는데">어떻게 사용하는데</h3>
<p>Serializable은 Java 내장 지원을 하고 있고 Kotlin에서 사용할 경우에는 Kotlinx Serialization 라이브러리에서 제공하는 기능을 사용하면 쉽게 사용 가능하다.</p>
<p>나는 현재 kotlin을 주로 사용하고 있기 때문에 kotlin에서 사용하는 방법에 대해 알아보려고한다.
<br></br></p>
<ol>
<li>일단, <code>kotlinx.serialization</code> 라이브러리 추가해줘야 한다.
프로젝트의 build.gradle에 아래 코드를 추가한다.<pre><code class="language-kotlin">dependencies {
 implementation(&quot;org.jetbrains.kotlinx:kotlinx-serialization-json:1.6.0&quot;)
}</code></pre>
<br></br></li>
<li>그 다음 plugins 블록에도 <code>kotlinx-serialization</code>을 추가한다<pre><code class="language-kotlin">plugins {
 kotlin(&quot;plugin.serialization&quot;) version &quot;1.9.0&quot; // 사용 중인 Kotlin 버전에 맞춰 설정
}</code></pre>
<br></br></li>
<li>다음은 직렬화가 필요한 class에 <code>@Serializable</code> 어노테이션 추가<pre><code class="language-kotlin">import kotlinx.serialization.Serializable
</code></pre>
</li>
</ol>
<p>@Serializable
data class Person(
    val name: String,
    val age: Int
)</p>
<pre><code>&lt;br&gt;&lt;/br&gt;
4. _JSON 직렬화 및 역직렬화도 가능하다_
`kotlinx.serialization.json.Json`을 사용해 객체를 JSON으로 변환하거나 JSON을 객체로 변환할 수 있음
```kotlin
import kotlinx.serialization.*
import kotlinx.serialization.json.*

fun main() {
    val person = Person(&quot;Alice&quot;, 25)

    // 직렬화: 객체 -&gt; JSON 문자열
    val json = Json.encodeToString(person)
    println(&quot;직렬화된 JSON: $json&quot;)

    // 역직렬화: JSON 문자열 -&gt; 객체
    val deserializedPerson = Json.decodeFromString&lt;Person&gt;(json)
    println(&quot;역직렬화된 객체: $deserializedPerson&quot;)
}</code></pre><p>직렬화된 JSON: {&quot;name&quot;:&quot;Alice&quot;,&quot;age&quot;:25}
역직렬화된 객체: Person(name=Alice, age=25)</p>
<hr>
<h3 id="지금까지-자바에서-말하는-serializable에-대해-설명하고-사용법은-왜-코틀린에서-사용하는-serializable로-알려줘요-둘이-같은-거-아니에요">지금까지 자바에서 말하는 Serializable에 대해 설명하고 사용법은 왜 코틀린에서 사용하는 Serializable로 알려줘요? 둘이 같은 거 아니에요?!</h3>
<h4 id="java-serializable와-kotlinx-serialization-비교">Java Serializable와 Kotlinx Serialization 비교</h4>
<p>참고로 도입부에서 말한 _<strong>바이트스트림</strong>_으로 변환해주는 직렬화는 <strong>자바에서의 Serializable</strong>을 말한 거고,
<strong>kotlin에서 사용하는 Kotlinx Serialization와는 다르다.</strong> 밑에 표에서 살펴보자!
<br></br></p>
<table>
<thead>
<tr>
<th><strong>구분</strong></th>
<th><strong>Java Serializable</strong></th>
<th><strong>Kotlinx Serialization</strong></th>
</tr>
</thead>
<tbody><tr>
<td><strong>직렬화 포맷</strong></td>
<td>바이트 스트림</td>
<td>JSON, ProtoBuf, CBOR 등 다양한 포맷 지원</td>
</tr>
<tr>
<td><strong>구현 방식</strong></td>
<td>JVM에 종속적인 방식</td>
<td>JVM 독립적으로 설계, 가볍고 빠름</td>
</tr>
<tr>
<td><strong>사용성</strong></td>
<td>단순히 바이트 스트림 처리용</td>
<td>다양한 포맷 지원 및 더 나은 유연성 제공</td>
</tr>
<tr>
<td><strong>속도 및 성능</strong></td>
<td>비교적 느림</td>
<td>최적화되어 있어 빠르고 가벼움</td>
</tr>
<tr>
<td><strong>사용 대상</strong></td>
<td>파일 저장 및 네트워크 전송용</td>
<td>주로 JSON, API 데이터 교환 등 현대적 사용 사례에 적합</td>
</tr>
<tr>
<td><strong>추가 기능</strong></td>
<td>제한적 (<code>transient</code> 키워드 등)</td>
<td>기본값 처리, @Transient, 다양한 포맷 지원 등 고급 기능 제공</td>
</tr>
<tr>
<td><strong>의존성</strong></td>
<td>자바 기본 라이브러리 포함</td>
<td><code>kotlinx.serialization</code> 라이브러리 추가 필요</td>
</tr>
</tbody></table>
<p><br></br></p>
<hr>
<p>흠.. 그렇군
그럼 또</p>
<h3 id="parcelize는-뭔데">@Parcelize는 뭔데?</h3>
<p>뭐 data class위에 어노테이션 갖다 붙이면 다 직렬화/역직렬화 알아서 시켜주는 것 같죠?
저도 뭣 모르고 사용하던 코흘리개 시절에는 둘의 차이점도 자세히 모르고 갖다 붙이면 알아서 변환해주것지.. 하고 썼슴미다.. 
<img src="https://velog.velcdn.com/images/devel_liz/post/d5a8cddb-ca32-456f-b54a-c767e96788c7/image.png" alt=""></p>
<p>둘 다 직렬화/역직렬화 해주는 건 맞는데 어떻게 해주는지, 그리고 어떤 상황에 사용하는지를 알고 써야 찐 개발자라고 할 수 있죠.. maybe</p>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/71ebeb26-7a5b-49ac-86e3-de31cf7d53b3/image.png" alt="">
<del>(저 아님)</del></p>
<p><strong>@Parcelize</strong>는 번역하면 &quot;소포화&quot;, 발음은 &quot;파썰라이즈&quot;이다.
<strong>@Parcelize</strong>는 Kotlin에서 <code>Parcelable</code> 인터페이스를 자동으로 구현해주는 어노테이션이다.
이 어노테이션을 사용하면, <strong>직렬화/역직렬화</strong> 과정을 매우 간편하게 처리할 수 있다.</p>
<h4 id="parcelable은-또-뭔데요">Parcelable은 또 뭔데요?</h4>
<p><code>Parcelable</code>은  Android 시스템에 최적화된 직렬화 방식이다.
즉, Android에서 객체를 Intent, Bundle 등을 통해 전달할 수 있도록 하는 인터페이스</p>
<p><strong>@Parcelize</strong>를 함께 사용하면 Kotlin에서 <strong>Parcelable</strong>을 쉽게 구현할 수 있도록 도와준다.
<strong>@Parcelize</strong>를 사용하지 않을 경우 <code>writeToParcel()</code>와 <code>describeContents()</code> 메소드를 직접 구현해야 한다.</p>
<hr>
<h3 id="왜-intent-bundle-등을-통해-전달할-때는-parcelable를-쓰라고-하는-거지">왜 Intent, Bundle 등을 통해 전달할 때는 Parcelable를 쓰라고 하는 거지?</h3>
<p><strong>Parcelable</strong>을 Intent, Bundle 등을 통해 객체를 전달할 때 사용하는 것이 권장되는 이유는 성능과 효율성 때문이다.
<strong>Serializable</strong>도 직렬화 방식으로 사용할 수 있지만, <strong>Parcelable</strong>은 Android에서 더 최적화된 방식으로 데이터를 전달하는 데 유리하다.
<br></br></p>
<ul>
<li>성능(속도)이 뛰어난 이유
<strong>Parcelable</strong>은 Android 시스템에 맞게 최적화되어 있어서, 객체를 <strong>Parcel</strong>에 직렬화하고 이를 <strong>Intent</strong>나 <strong>Bundle</strong>로 전달할 때 훨씬 더 빠르고 메모리 효율적입니다.
<br></br>
<em>잠깐만.. Parcel은 또 뭐야?</em>
( <em>Parcel에 대해 궁금하다면 ? =&gt; <a href="https://developer.android.com/reference/android/os/Parcel">https://developer.android.com/reference/android/os/Parcel</a></em> )
<br></br></li>
</ul>
<p><code>Pacel</code>은 Android 플랫폼에 특화된 클래스이고, 직렬화된 데이터를 담는 컨테이너인데
이 <code>Parcel</code>을 사용할 수 있는 것이 바로 <code>Parcelable</code>이다.
<code>Serializable</code>은 <code>Parcel</code>을 사용할 수 없다..!!</p>
<p>즉, <code>Parcelable</code>은 Android의 <code>Parcel</code> 구조에 맞게 설계되어 있어, <strong>객체를 전달하는 데 필요한 메모리 양이 적다.</strong>
이로 인해, 대규모 데이터를 처리할 때 메모리 소비가 적고 효율적이다.</p>
<h4 id="parcelable-작동방식">Parcelable 작동방식</h4>
<ol>
<li>데이터를 직렬화/역직렬화 해서 <strong>Parcel</strong>에 저장한다.</li>
<li>그리고 Intent안에 Parcel 객체를 담아 <strong>Activity</strong>나 <strong>Service</strong>에 전달하고, 이 객체는 <strong>Intent</strong>가 도착한 곳에서 <strong>Parcel</strong>을 역직렬화하여 다시 원래의 객체로 복원할 수 있다.
<br></br></li>
</ol>
<h3 id="📌-결론-intent를-통해-데이터-전달-시-parcelable은-parcel-에-담아-전달-serializable은-바이트스트림으로-변환하여-전달">📌 결론: Intent를 통해 데이터 전달 시 Parcelable은 Parcel 에 담아 전달! Serializable은 바이트스트림으로 변환하여 전달!</h3>
<hr>
<h3 id="정리해-봅시다">정리해 봅시다</h3>
<ol>
<li>Serializable과 Pacelable은 어떤 용도로 사용하나요?</li>
</ol>
<p>-&gt; 객체 또는 데이터를 직렬화/역직렬화할 때 사용하는 인터페이스입니다.</p>
<ol start="2">
<li>자바에서의 직렬화가 뭔가요?</li>
</ol>
<p>-&gt; 객체 또는 데이터를 외부 시스템에서도 사용할 수 있도록 byte-stream 형태로 변환하는 기술을 의미합니다.</p>
<ol start="3">
<li><p>Serializable은 어떻게 직렬화시키나요?
JVM이 자동으로 ObjectOutputStream을 통해 객체의 필드를 바이트 스트림으로 변환합니다.</p>
</li>
<li><p>Pacelable은 어떻게 직렬화시키나요?</p>
</li>
</ol>
<p>-&gt; Android에서 객체 데이터를 Parcel에 쓰고 읽는 방식으로 직렬화를 수행합니다.</p>
<ol start="5">
<li>Serializable이 Pacelable에 비해 성능이 떨어진다는 말이 나오는 이유가 뭘까요?</li>
</ol>
<p>-&gt; Serializable은 리플렉션을 통해 객체의 메타데이터를 동적으로 검색하고 직렬화/역직렬화 하는 반면, Pacelable은 리플렉션을 사용하지 않고 필요한 필드만 개발자가 명시적으로 Parcel에 어떤 데이터를 저장할지, 그리고 어떻게 복원할지를 정의합니다.</p>
<ol start="6">
<li>리플렉션이 뭔가요?</li>
</ol>
<p>-&gt; 런타임에 클래스, 메서드, 필드 등의 정보를 동적으로 탐색하고 수정할 수 있는 기능입니다.</p>
<hr>
<p><br></br></p>
<p>추가로 <code>Serializable</code>과 <code>Parcelable</code>에 대해 이해하기 쉽게 정리된 영상 자료 및 글을 첨부합니다</p>
<ul>
<li><a href="https://youtu.be/-_scGU1nkPg?si=zmwvdjr1snXnbzxE">https://youtu.be/-_scGU1nkPg?si=zmwvdjr1snXnbzxE</a></li>
<li><a href="https://medium.com/jaesung-dev/android-%EC%A7%81%EB%A0%AC%ED%99%94%EC%99%80-%EC%97%AD%EC%A7%81%EB%A0%AC%ED%99%94-18fd04f1c0ed">https://medium.com/jaesung-dev/android-%EC%A7%81%EB%A0%AC%ED%99%94%EC%99%80-%EC%97%AD%EC%A7%81%EB%A0%AC%ED%99%94-18fd04f1c0ed</a>
<br></br></li>
</ul>
<p><em>끝으로..!</em></p>
<p>본 글에서 다른 의견이 있거나 추가적으로 공유하고 싶은 내용이 있다면 댓글로 남겨주시면 저에게 엄청난 도움이 됩니다</p>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/40e09688-8393-4119-a0f9-75b7574e4dd7/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 가까운 1 찾기]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EA%B0%80%EA%B9%8C%EC%9A%B4-1-%EC%B0%BE%EA%B8%B0</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EA%B0%80%EA%B9%8C%EC%9A%B4-1-%EC%B0%BE%EA%B8%B0</guid>
            <pubDate>Thu, 02 Jan 2025 13:31:50 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p>문제대로 풀었는데 계속 답이 안 나와서 질문하기 페이지에 봤더니 문제가 잘못 나와있었다.
idx보다 크면서 x -&gt; idx보다 같거나 크면서 o
문제 풀 때 참고하시길...!
<img src="https://velog.velcdn.com/images/devel_liz/post/c6550534-0071-40e2-80e4-5cd3abf83672/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(arr: IntArray, idx: Int): Int {
          for (i in idx until arr.size) {
            if (arr[i] == 1) {
                return i
            }
        }
        return -1
    }

}</code></pre>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(arr: IntArray, idx: Int): Int = (idx until arr.size).firstOrNull { arr[it] == 1 } ?: -1
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li>firstOrNull { arr[it] == 1 }<ul>
<li>firstOrNull은 컬렉션에서 첫 번째로 조건을 만족하는 요소를 찾는 함수입니다.</li>
<li>arr[it] == 1은 arr 배열의 it번째 인덱스에 해당하는 값이 1인지 확인하는 조건입니다.</li>
<li>it은 firstOrNull 내에서 자동으로 제공되는 현재 순회 중인 인덱스를 나타냅니다.</li>
<li>만약 arr[it] == 1인 요소가 있으면 그 첫 번째 인덱스를 반환합니다. 만약 조건을 만족하는 요소가 없다면 null을 반환합니다.</li>
</ul>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 카운트 다운]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%B9%B4%EC%9A%B4%ED%8A%B8-%EB%8B%A4%EC%9A%B4</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%B9%B4%EC%9A%B4%ED%8A%B8-%EB%8B%A4%EC%9A%B4</guid>
            <pubDate>Thu, 02 Jan 2025 13:01:43 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/c0c97988-3b08-4eab-95ce-2db4098d251d/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(start_num: Int, end_num: Int): IntArray {
            return (end_num..start_num step 1).toList().reversed().toIntArray()
    }
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<p>첫번째 풀이는 좋아요가 많은 풀이고 두번째는 개인적으로 흥미롭게 느껴 가지고 온 문제 풀이다.</p>
<pre><code class="language-kotlin">class Solution {
    fun solution(start: Int, end: Int) = (end..start).toList().sortedDescending()
}</code></pre>
<pre><code class="language-kotlin">class Solution {
    fun solution(start: Int, end: Int): IntArray = (start downTo end).toList().toIntArray()
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li>(start downTo end)<ul>
<li><code>downTo</code>의 특징<ul>
<li>내림차순 범위: downTo는 주어진 start 값에서 end 값까지 내림차순으로 값을 반환하는 <strong>IntProgression</strong>을 만듭니다.</li>
<li>step(간격)을 설정하지 않으면 기본값으로 1씩 감소하는 범위가 생성됩니다.<pre><code class="language-kotlin">val result = (10 downTo 3).toList()
println(result)  // 출력: [10, 9, 8, 7, 6, 5, 4, 3]

</code></pre>
</li>
</ul>
</li>
</ul>
</li>
</ul>
<pre><code> val range = 10 downTo 1 step 2
 println(range.toList())  // 출력: [10, 8, 6, 4, 2]</code></pre><p>위 예시는 step을 2로 설정하여 10부터 1까지 내림차순으로 2씩 감소하는 범위를 생성합니다.</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 글자 지우기]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EA%B8%80%EC%9E%90-%EC%A7%80%EC%9A%B0%EA%B8%B0</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EA%B8%80%EC%9E%90-%EC%A7%80%EC%9A%B0%EA%B8%B0</guid>
            <pubDate>Thu, 02 Jan 2025 12:42:15 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/b2f0dfc7-cbb8-4941-aae2-e3cc64e4bc4e/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String, indices: IntArray): String {
            return my_string.filterIndexed{ i, _ -&gt; i !in indices}
}
}
</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String, indices: IntArray): String {
        return my_string.filterIndexed { index, w -&gt; index !in indices }
    }
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li>filterIndexed<ul>
<li><code>filterIndexed</code>는 문자열이나 리스트 등 인덱스와 값을 동시에 가져오면서 조건에 맞는 요소만 남기는 함수입니다.</li>
<li>각 요소를 순회하며 <strong>인덱스(index)</strong>와 <strong>값(value)</strong>을 받아옵니다.</li>
<li>특정 조건에 맞는 요소만 남겨 새롭게 반환합니다.</li>
</ul>
</li>
<li>in<ul>
<li>정의: in은 어떤 값이 특정 컬렉션(리스트, 배열, Set 등)에 포함되어 있는지 검사하는 연산자입니다.</li>
<li>동작 방식:
x in collection은 내부적으로 collection.contains(x)를 호출합니다.
결과는 Boolean 값(true 또는 false)으로 반환됩니다.<pre><code class="language-kotlin">val indices = intArrayOf(0, 2, 4)
</code></pre>
</li>
</ul>
</li>
</ul>
<p>// 2가 indices에 있는지 확인
println(2 in indices) // true</p>
<p>// 3이 indices에 있는지 확인
println(3 in indices) // false</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 배열 만들기 1]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%B0%B0%EC%97%B4-%EB%A7%8C%EB%93%A4%EA%B8%B0-1</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%B0%B0%EC%97%B4-%EB%A7%8C%EB%93%A4%EA%B8%B0-1</guid>
            <pubDate>Thu, 02 Jan 2025 11:54:08 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/884c409e-7c96-4bd1-895a-faf76a3837bf/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(n: Int, k: Int): IntArray {
        return (1..n).filter{ it % k == 0 }.sorted().toIntArray()
    }
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(n: Int, k: Int) = (k..n step k).toList()
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li><p>(1..n)</p>
<ul>
<li>1에서 n까지의 값을 포함하는 <strong>정수 범위(IntRange)</strong>를 생성합니다.</li>
<li>시작 값(1)부터 끝 값(n)까지 포함됩니다.</li>
<li>반환 타입: IntRange.</li>
<li>고차 함수 사용 가능: .filter, .map, .forEach 등.<pre><code class="language-kotlin">val range = 1..5
println(range.toList())  // 출력: [1, 2, 3, 4, 5]</code></pre>
</li>
</ul>
</li>
<li><p>sorted()</p>
<ul>
<li>컬렉션의 요소를 오름차순으로 정렬한 새로운 리스트를 반환합니다.</li>
<li>특징:<ul>
<li>원본 데이터를 변경하지 않고, 정렬된 새로운 컬렉션을 반환합니다.</li>
<li>기본적으로 숫자는 오름차순, 문자열은 사전순 정렬됩니다.</li>
<li>컬렉션(리스트, 배열 등)에서 사용 가능.<pre><code class="language-kotlin">val list = listOf(3, 1, 4, 2)
println(list.sorted())  // 출력: [1, 2, 3, 4]

</code></pre>
</li>
</ul>
</li>
</ul>
</li>
</ul>
<ul>
<li>(k..n step k)<ul>
<li>k부터 n까지의 범위를 생성하되, 간격이 k인 정수 범위를 만듭니다.</li>
<li>특징:<ul>
<li>시작 값(k), 끝 값(n), 간격(step)을 지정할 수 있습니다.</li>
<li>반환 타입: IntProgression.</li>
<li>기본 범위(1..n)와 달리 step 간격으로 값을 포함.<pre><code class="language-kotlin">val range = 2..10 step 2
println(range.toList())  // 출력: [2, 4, 6, 8, 10]
</code></pre>
</li>
</ul>
</li>
</ul>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 문자 개수 세기]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%AC%B8%EC%9E%90-%EA%B0%9C%EC%88%98-%EC%84%B8%EA%B8%B0</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%AC%B8%EC%9E%90-%EA%B0%9C%EC%88%98-%EC%84%B8%EA%B8%B0</guid>
            <pubDate>Mon, 23 Dec 2024 02:16:08 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/4ae31f75-67b2-437f-92b1-687c1f58ceb1/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String): IntArray {
        val alphabetList = (&#39;A&#39;..&#39;Z&#39;).toList() + (&#39;a&#39;..&#39;z&#39;).toList()
        val charFrequency = my_string.groupingBy { it }.eachCount()

        return alphabetList.map { charFrequency[it] ?: 0 }.toIntArray()
    }
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String): IntArray {
        return ((&#39;A&#39;..&#39;Z&#39;).map { alpha -&gt; my_string.count { it == alpha } } +
        (&#39;a&#39;..&#39;z&#39;).map { alpha -&gt; my_string.count { it == alpha } }).toIntArray()
    }
}</code></pre>
<p>주어진 코드에서 count의 역할은 문자열(my_string)에서 특정 문자의 개수를 세는 것입니다.</p>
<p><strong>역할 설명</strong>
my_string.count { it == alpha }
my_string의 각 문자(it)가 alpha와 같은지 확인합니다.
조건(it == alpha)을 만족하는 문자의 개수를 세어 반환합니다.</p>
<p><strong>동작 방식</strong>
(&#39;A&#39;..&#39;Z&#39;)와 (&#39;a&#39;..&#39;z&#39;) 범위의 각각의 문자(alpha)에 대해 count를 호출합니다.
예를 들어, alpha가 &#39;A&#39;라면 my_string에서 &#39;A&#39;가 몇 번 등장하는지 세어 반환합니다.</p>
<p><strong>간략한 요약</strong>
count는 문자열에서 특정 조건(예: 특정 문자와 일치)을 만족하는 요소의 개수를 세는 데 사용됩니다.
이 코드에서는 대문자와 소문자의 각각의 등장 횟수를 계산하는 역할을 합니다.</p>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li><p>groupingBy</p>
<ul>
<li>컬렉션을 특정 기준으로 그룹화할 때 사용합니다.</li>
<li>결과는 Grouping 객체로 반환되며, 이를 통해 추가적인 연산(예: 개수 세기)을 수행할 수 있습니다.<pre><code class="language-kotlin">val words = listOf(&quot;apple&quot;, &quot;banana&quot;, &quot;cherry&quot;, &quot;apple&quot;)
val grouped = words.groupingBy { it.first() } // 첫 글자로 그룹화</code></pre>
</li>
</ul>
</li>
<li><p>eachCount</p>
<ul>
<li>groupingBy로 생성된 Grouping 객체에 사용하여, 각 그룹에 포함된 요소의 개수를 계산합니다.<pre><code class="language-kotlin">val words = listOf(&quot;apple&quot;, &quot;banana&quot;, &quot;cherry&quot;, &quot;apple&quot;)
val counts = words.groupingBy { it.first() }.eachCount()
println(counts) // {a=2, b=1, c=1}</code></pre>
</li>
</ul>
</li>
<li><p>count는</p>
<ul>
<li>count는 컬렉션이나 문자열에서 특정 조건을 만족하는 요소의 개수를 반환하는 함수입니다.<ul>
<li>조건이 없으면 전체 개수를 반환합니다.</li>
<li>조건이 있으면 해당 조건을 만족하는 요소의 개수를 반환합니다.<pre><code class="language-kotlin">val text = &quot;hello&quot;
val totalCount = text.count()              // 전체 문자 개수: 5
val lCount = text.count { it == &#39;l&#39; }      // &#39;l&#39;의 개수: 2</code></pre>
</li>
</ul>
</li>
</ul>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[[Compose] ConstraintLayout]]></title>
            <link>https://velog.io/@devel_liz/Compose-ConstraintLayout-b07vusi6</link>
            <guid>https://velog.io/@devel_liz/Compose-ConstraintLayout-b07vusi6</guid>
            <pubDate>Thu, 19 Dec 2024 12:03:20 GMT</pubDate>
            <description><![CDATA[<p><em><strong>xml에 ConstraintLayout 있고, compose에도 ConstraintLayout이 있다.</strong></em></p>
<p>xml에서는 ConstraintLayout을 사용할 경우 중첩을 줄이고, 복잡한 UI를 효율적으로 배치할 수 있으며, 다양한 화면 크기와 해상도에 적응하는 동적인 레이아웃을 구현할 수 있기 때문에 xml에서 constraintLayout이 권장되었다.</p>
<p>하지만 compose는 이미 compose의 기본 레이아웃(Column, Row, Box)이 강력하며, 중첩된 구조를 통해 다양한 배치를 쉽게 구현할 수 있기 때문에 필수 사항은 아니다.</p>
<p>compose에서 ConstraintLayout은 <strong>더 복잡한 정렬 요구사항이 있거나 더 큰 레이아웃을 구현할 때 유용하다.</strong></p>
<hr>
<h3 id="사용법">사용법</h3>
<ol>
<li><p>build.grale에 추가하기</p>
<pre><code class="language-kotlin">implementation &quot;androidx.constraintlayout:constraintlayout-compose:1.0.1&quot;</code></pre>
</li>
<li><p>createRefs() 설정하기</p>
<pre><code class="language-kotlin">val (redBox, magentaBox, greenBox, yellowBox) = createRefs()</code></pre>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/10bf66a2-5101-47c2-9673-4577cc178d83/image.png" alt="">
다음과같이 createRefs()는 컴포넌트를 16개까지 지원한다 16개 넘게 사용할 경우에는 createRefs()를 추가 생성하면 된다.</p>
</li>
<li><p>constrainAs, linkTo 설정하기</p>
<pre><code class="language-kotlin">     Box(modifier = Modifier
         .size(40.dp)
         .background(Color.Magenta)
         .constrainAs(magentaBox) {
             start.linkTo(parent.start)
             end.linkTo(parent.end)
         })</code></pre>
<p>constrainAs 괄호 안에는 해당 박스에 이름을 넣어주었고
start.linkTo(parent.start) 라는 뜻은 내 start 라인을 parent의 start라인에 붙이겠단 뜻이다</p>
</li>
<li><p>centrtTo(), centerHorizontallyTo(), centerVerticallyTo()
괄호 안에 레퍼런스를 넣어주면 그 레퍼런스를 기준으로 중앙 배치가 된다.
어떻게 중앙 배치가 되는지는 뜻을 그대로 해석해서 사용하면 된다.</p>
</li>
</ol>
<hr>
<p>그렇게 테스트해본 constraintLayout 샘플 코드를 올려놓겠다..</p>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/a38776bc-a4fb-4f2c-a640-d6288f3a4631/image.png" alt=""></p>
<pre><code class="language-kotlin">class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            MyApplicationTheme {
                // A surface container using the &#39;background&#39; color from the theme
                Surface(modifier = Modifier.fillMaxSize(),
                    color = MaterialTheme.colorScheme.background) {
                    ConstraintLayoutEx()
                }
            }
        }
    }
}

@Composable
fun ConstraintLayoutEx() {
    ConstraintLayout(modifier = Modifier.fillMaxSize()) {
        val (redBox, magentaBox, greenBox, yellowBox) = createRefs()


        Box(modifier = Modifier
            .size(40.dp)
            .background(Color.Red)
            .constrainAs(redBox) {
                bottom.linkTo(parent.bottom, margin = 8.dp)
                end.linkTo(parent.end, margin = 8.dp)
            })
        Box(modifier = Modifier
            .size(40.dp)
            .background(Color.Magenta)
            .constrainAs(magentaBox) {
                start.linkTo(parent.start)
                end.linkTo(parent.end)
            })
        Box(modifier = Modifier
            .size(40.dp)
            .background(Color.Green)
            .constrainAs(greenBox) {
                centerTo(parent)
            })
        Box(modifier = Modifier
            .size(40.dp)
            .background(Color.Yellow)
            .constrainAs(yellowBox) {
                start.linkTo(magentaBox.end)
                top.linkTo(magentaBox.bottom)
            })
    }
}


@Preview(showBackground = true)
@Composable
fun DefaultPreview() {
    MyApplicationTheme {
        ConstraintLayoutEx()
    }
}</code></pre>
<hr>
<h3 id="constraintset도-알아보자">ConstraintSet도 알아보자</h3>
<p>ConstraintSet을 이용해 constraintLayout을 밖으로 빼내보자
위  코드에서는 modifier 안에 모든 제약들이 있었다.
그 제약들을 별도로 설정하는 방법을 지금부터 알아보자.</p>
<ol>
<li><p>ConstraintSet 안에 레퍼런스를 만들어주자.</p>
<pre><code class="language-kotlin"> val constraintSet = ConstraintSet{
     val redBox = createRefFor(&quot;redBox&quot;)
     val magentaBox = createRefFor(&quot;magentaBox&quot;)
     val greenBox = createRefFor(&quot;greenBox&quot;)
     val yellowBox = createRefFor(&quot;yellowBox&quot;)
 }</code></pre>
</li>
<li><p>constrian으로 제약을 옮겨주자</p>
<pre><code class="language-kotlin"> val constraintSet = ConstraintSet {
     val redBox = createRefFor(&quot;redBox&quot;)
     val magentaBox = createRefFor(&quot;magentaBox&quot;)
     val greenBox = createRefFor(&quot;greenBox&quot;)
     val yellowBox = createRefFor(&quot;yellowBox&quot;)

     constrain(redBox) {
         bottom.linkTo(parent.bottom, margin = 8.dp)
         end.linkTo(parent.end, margin = 8.dp)
     }
     constrain(magentaBox) {
         start.linkTo(parent.start)
         end.linkTo(parent.end)
     }
     constrain(greenBox) {
         centerTo(parent)
     }
     constrain(yellowBox) {
         start.linkTo(magentaBox.end)
         top.linkTo(magentaBox.bottom)
     }
 }</code></pre>
<ol start="3">
<li><p>layoutId 설정하기</p>
<pre><code class="language-kotlin">ConstraintLayout(modifier = Modifier.fillMaxSize()) {

  Box(modifier = Modifier
      .size(40.dp)
      .background(Color.Red)
      .layoutId(&quot;redBox&quot;)
  )
  Box(modifier = Modifier
      .size(40.dp)
      .background(Color.Magenta)
      .layoutId(&quot;magentaBox&quot;)
  )
  Box(modifier = Modifier
      .size(40.dp)
      .background(Color.Green)
      .layoutId(&quot;greenBox&quot;)
  )

  Box(modifier = Modifier
      .size(40.dp)
      .background(Color.Yellow)
      .layoutId(&quot;yellowBox&quot;)
  )
}</code></pre>
</li>
<li><p>ConstraintLayout과 ConstarintSet을 연결 시키자</p>
<pre><code class="language-kotlin">ConstraintLayout(
  constraintSet,
  modifier = Modifier.fillMaxSize()) {

  Box(modifier = Modifier
      .size(40.dp)
      .background(Color.Red)
      .layoutId(&quot;redBox&quot;)
  )
  Box(modifier = Modifier
      .size(40.dp)
      .background(Color.Magenta)
      .layoutId(&quot;magentaBox&quot;)
  )
  Box(modifier = Modifier
      .size(40.dp)
      .background(Color.Green)
      .layoutId(&quot;greenBox&quot;)
  )

  Box(modifier = Modifier
      .size(40.dp)
      .background(Color.Yellow)
      .layoutId(&quot;yellowBox&quot;)
  )
}
</code></pre>
</li>
</ol>
</li>
</ol>
<hr>
<p>전체 코드를 보고 ConstraintSet을 쓰기 전과 쓴 후 어떻게 다른지 비교해 봅시다!</p>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/9bb372c1-5f05-4223-9207-f8eb315299dc/image.png" alt=""></p>
<pre><code class="language-kotlin">class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            MyApplicationTheme {
                // A surface container using the &#39;background&#39; color from the theme
                Surface(modifier = Modifier.fillMaxSize(),
                    color = MaterialTheme.colorScheme.background) {
                    ConstraintLayoutEx()
                }
            }
        }
    }
}

@Composable
fun ConstraintLayoutEx() {
    val constraintSet = ConstraintSet {
        val redBox = createRefFor(&quot;redBox&quot;)
        val magentaBox = createRefFor(&quot;magentaBox&quot;)
        val greenBox = createRefFor(&quot;greenBox&quot;)
        val yellowBox = createRefFor(&quot;yellowBox&quot;)

        constrain(redBox) {
            bottom.linkTo(parent.bottom, margin = 8.dp)
            end.linkTo(parent.end, margin = 8.dp)
        }
        constrain(magentaBox) {
            start.linkTo(parent.start)
            end.linkTo(parent.end)
        }
        constrain(greenBox) {
            centerTo(parent)
        }
        constrain(yellowBox) {
            start.linkTo(magentaBox.end)
            top.linkTo(magentaBox.bottom)
        }
    }
    ConstraintLayout(
        constraintSet,
        modifier = Modifier.fillMaxSize()) {

        Box(modifier = Modifier
            .size(40.dp)
            .background(Color.Red)
            .layoutId(&quot;redBox&quot;)
        )
        Box(modifier = Modifier
            .size(40.dp)
            .background(Color.Magenta)
            .layoutId(&quot;magentaBox&quot;)
        )
        Box(modifier = Modifier
            .size(40.dp)
            .background(Color.Green)
            .layoutId(&quot;greenBox&quot;)
        )

        Box(modifier = Modifier
            .size(40.dp)
            .background(Color.Yellow)
            .layoutId(&quot;yellowBox&quot;)
        )
    }
}


@Preview(showBackground = true)
@Composable
fun DefaultPreview() {
    MyApplicationTheme {
        ConstraintLayoutEx()
    }
}</code></pre>
<hr>
<p>끝으로 이런 의문이 들 수도 있다.
아니, <strong>ConstraintLayout으로 구현 가능한데 왜 굳이 ConstraintSet을 사용하지?</strong></p>
<p>이러한 이유 때문에 ConstraintSet을 사용한다</p>
<ol>
<li>레이아웃 변경을 동적으로 처리</li>
</ol>
<ul>
<li>ConstraintSet은 앱 실행 중에 레이아웃의 제약 조건을 동적으로 업데이트할 수 있도록 해줍니다.<ul>
<li>예시: 버튼 클릭 시 뷰의 위치를 변경하거나, 특정 이벤트에 따라 레이아웃을 조정해야 할 때.</li>
</ul>
</li>
</ul>
<ol start="2">
<li>제약 조건의 재사용 가능</li>
</ol>
<ul>
<li>반복적으로 사용되는 제약 조건을 하나의 ConstraintSet으로 정의하고 재사용할 수 있습니다.<ul>
<li>예시: 다수의 화면에서 동일한 제약 조건을 적용해야 할 경우, 코드 중복을 줄이고 유지보수성을 높일 수 있습니다.</li>
</ul>
</li>
</ul>
<ol start="3">
<li>애니메이션과 전환 구현</li>
</ol>
<ul>
<li>ConstraintSet은 애니메이션과 전환을 구현할 때도 유용합니다.<ul>
<li>예시: 두 개의 ConstraintSet을 정의하고, 이를 TransitionManager와 함께 사용하면 자연스러운 애니메이션 효과를 줄 수 있습니다.</li>
</ul>
</li>
</ul>
<ol start="4">
<li>ConstraintLayout 대비 코드 간결화</li>
</ol>
<ul>
<li>ConstraintLayout에 직접 제약 조건을 정의하면 코드가 길고 가독성이 떨어질 수 있습니다.</li>
<li>ConstraintSet은 제약 조건을 구조적으로 정의하므로, 코드가 더 읽기 쉽고 유지보수가 간편합니다.</li>
</ul>
<hr>
<h3 id="결론">결론</h3>
<p><code>ConstraintSet</code>은 다음과 같은 경우 유용하다.</p>
<ul>
<li>실행 중 레이아웃 변경이 필요한 경우</li>
<li>제약 조건을 <strong>재사용</strong>하려는 경우</li>
<li>애니메이션이나 전환 효과를 구현할 때.</li>
</ul>
<p>단순한 제약 조건이라면 <code>ConstraintLayout</code>만으로도 충분하지만, 복잡한 레이아웃 변경이나 재사용성이 중요한 경우 <code>ConstraintSet</code>이 더 효율적입니다.</p>
<hr>
<p>질문은 언제나 환영입니다!! 👍💚</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] qr code]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-qr-code</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-qr-code</guid>
            <pubDate>Thu, 19 Dec 2024 05:54:46 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/dccd363b-32f3-474c-8535-56ea2181942c/image.png" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/46ebfa22-407f-4738-aa1f-c88ce3db967f/image.png" alt="">
<code>q</code>로 나눈 나머지가 1인 인덱스의 문자들을 앞에서부터 순서대로 이어 붙이면 &quot;jerry&quot;가 되므로 이를 return 합니다.
<img src="https://velog.velcdn.com/images/devel_liz/post/9cb86e1b-2a65-465c-9d04-e2d3769ed2ba/image.png" alt="">
<code>q</code>로 나눈 나머지가 1인 인덱스의 문자들을 앞에서부터 순서대로 이어 붙이면 &quot;programmers&quot;가 되므로 이를 return 합니다.</p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(q: Int, r: Int, code: String): String {
      return  code.chunked(q)
            .filter{ it.length &gt; r }
            .map{ it[r] }
            .joinToString(&quot;&quot;)
    }
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(q: Int, r: Int, code: String): String {
        return code.indices.filter { it % q == r }.joinToString(&quot;&quot;) { code[it].toString() }
    }
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li><p>indices</p>
<ul>
<li><strong>indices</strong>는 컬렉션(예: String, List)의 유효한 인덱스를 범위로 반환하는 프로퍼티입니다.</li>
<li>예를 들어, 문자열이나 리스트의 모든 인덱스를 순회하거나 특정 범위를 설정할 때 유용합니다.<pre><code class="language-kotlin">val text = &quot;abc&quot;
println(text.indices)  // 출력값: 0..2</code></pre>
</li>
</ul>
</li>
<li><p>filter</p>
<ul>
<li><strong>filter</strong>는 컬렉션에서 주어진 조건을 만족하는 원소만 새로운 컬렉션으로 반환하는 함수입니다.</li>
<li>이 함수는 원본 컬렉션을 변경하지 않으며, 조건에 맞는 원소들만 추출하여 새로운 리스트를 생성합니다.<pre><code class="language-kotlin">val numbers = listOf(1, 2, 3, 4, 5)
val evenNumbers = numbers.filter { it % 2 == 0 }
println(evenNumbers)  // [2, 4]</code></pre>
</li>
</ul>
</li>
<li><p>joinToString(&quot;&quot;)</p>
<ul>
<li><strong>joinToString(&quot;&quot;)</strong>는 컬렉션의 모든 원소를 <strong>지정한 구분자</strong>(이 경우 &quot;&quot;`, 즉 공백 없이)로 결합하여 하나의 문자열로 반환하는 함수입니다.</li>
<li>구분자를 지정할 수 있으며, 기본적으로 각 원소를 문자열로 변환한 후 결합합니다.<pre><code class="language-kotlin">val words = listOf(&quot;hello&quot;, &quot;world&quot;)
val result = words.joinToString(&quot; &quot;)
println(result)  // &quot;hello world&quot;</code></pre>
</li>
</ul>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 세로 읽기]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%84%B8%EB%A1%9C-%EC%9D%BD%EA%B8%B0</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%84%B8%EB%A1%9C-%EC%9D%BD%EA%B8%B0</guid>
            <pubDate>Thu, 19 Dec 2024 05:09:51 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/697a7911-dcf9-4976-b31a-e78d6abcc610/image.png" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/7d499156-acf1-4fff-88fb-d5cb77e0e6ce/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String, m: Int, c: Int): String {

     return  my_string.chunked(m)
            .map{ it[c-1] }
            .joinToString(&quot;&quot;)
    }
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String, m: Int, c: Int): String {
        return my_string.chunked(m).map { it[c - 1] }.joinToString(&quot;&quot;)
    }
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li><p>chunked(size: Int)</p>
<ul>
<li>문자열을 <strong>지정한 크기(size)</strong>로 나누어 리스트를 생성합니다.</li>
<li>마지막 덩어리는 남은 글자만 포함합니다(길이가 부족해도 OK).<pre><code class="language-kotlin">val text = &quot;ihrhbakrfpndopljhygc&quot;
</code></pre>
</li>
</ul>
<p>// 4글자씩 끊어서 리스트 생성
val result = text.chunked(4)
println(result) // [ihrh, bakr, fpnd, oplj, hygc]</p>
</li>
<li><p>map</p>
<ul>
<li>map은 단순히 반복하는 역할이 아니라, 컬렉션의 각 원소를 특정 방식으로 변환하여 새로운 컬렉션을 생성하는 변환 메소드입니다.</li>
<li>변환 수행: 각 원소를 특정 방식으로 변환하여 새로운 컬렉션을 반환합니다.</li>
<li>원본 컬렉션은 변경되지 않음: map은 불변성을 유지하며, 원본 데이터는 그대로 두고 새로운 데이터를 생성합니다.</li>
<li>컬렉션의 모든 원소에 적용: 모든 원소에 대해 변환을 적용하고, 결과를 수집합니다.<pre><code class="language-kotlin">val numbers = listOf(1, 2, 3, 4, 5)
</code></pre>
</li>
</ul>
<p>// 각 원소를 2배로 변환
val doubled = numbers.map { it * 2 }
println(doubled) // [2, 4, 6, 8, 10]</p>
</li>
</ul>
<h4 id="map과-반복-비교">map과 반복 비교:</h4>
<p><strong>단순 반복 (for 또는 forEach)</strong>은 작업을 수행하고 끝나지만,
<strong>map</strong>은 변환 결과를 새로운 컬렉션으로 반환합니다.</p>
<pre><code class="language-kotlin">val numbers = listOf(1, 2, 3)

// 단순 반복
numbers.forEach { println(it * 2) } // 출력: 2, 4, 6

// 변환하여 새로운 리스트 생성
val doubled = numbers.map { it * 2 }
println(doubled) // [2, 4, 6]
</code></pre>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 문자열 뒤집기]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%AC%B8%EC%9E%90%EC%97%B4-%EB%92%A4%EC%A7%91%EA%B8%B0</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%AC%B8%EC%9E%90%EC%97%B4-%EB%92%A4%EC%A7%91%EA%B8%B0</guid>
            <pubDate>Thu, 19 Dec 2024 04:51:57 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/977eb909-a136-4555-8f5e-8f114d664977/image.png" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/91fd16bc-83e2-4313-9cad-3f10df840def/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String, s: Int, e: Int) = my_string.replaceRange(s..e, my_string.slice(s..e).reversed())
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(myString: String, s: Int, e: Int) = myString.substring(0, s) + myString.substring(s..e).reversed() + myString.substring(e + 1, myString.length)
}</code></pre>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li>replaceRange()<ul>
<li>문자열의 <strong>특정 범위(Range)</strong>를 지정하여 해당 부분을 교체합니다.</li>
<li>범위 표현으로 대체할 범위를 지정합니다.</li>
<li>반환값: 새로운 문자열 (원본 문자열은 변경되지 않음).<pre><code class="language-kotlin">val text = &quot;HelloWorld&quot;
</code></pre>
</li>
</ul>
</li>
</ul>
<p>// 범위 0..4의 문자열(&quot;Hello&quot;)을 &quot;Hi&quot;로 교체
val result = text.replaceRange(0..4, &quot;Hi&quot;)
println(result) // &quot;HiWorld&quot;</p>
<p>// 범위 5..9의 문자열(&quot;World&quot;)을 &quot;Everyone&quot;으로 교체
val result2 = text.replaceRange(5..9, &quot;Everyone&quot;)
println(result2) // &quot;HelloEveryone&quot;</p>
<pre><code>- replaceRange(startIndex, endIndex, replacement) 형식으로도 사용할 수 있습니다. 이 경우 endIndex는 포함되지 않음에 유의하세요
```kotlin
val result = text.replaceRange(0, 5, &quot;Hi&quot;) // &quot;HiWorld&quot;
</code></pre>]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 접두사인지 확인하기]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%A0%91%EB%91%90%EC%82%AC%EC%9D%B8%EC%A7%80-%ED%99%95%EC%9D%B8%ED%95%98%EA%B8%B0</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%A0%91%EB%91%90%EC%82%AC%EC%9D%B8%EC%A7%80-%ED%99%95%EC%9D%B8%ED%95%98%EA%B8%B0</guid>
            <pubDate>Thu, 19 Dec 2024 04:41:02 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/ecdc1650-b3a3-4396-9700-8db6ed860bca/image.png" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/0d9473ab-3653-4978-83da-af1239cfcb91/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String, is_prefix: String) = 
    if(my_string.startsWith(is_prefix)) 1 else 0
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String, is_prefix: String): Int = if (my_string.startsWith(is_prefix)) 1 else 0
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li><p>startsWith()</p>
<ul>
<li>접두사인지 확인하려면 startsWith() 메소드를 사용합니다.</li>
<li>설명: 문자열이 특정 접두사로 시작하는지 확인합니다.</li>
<li>반환값: Boolean (true 또는 false)<pre><code class="language-kotlin">val text = &quot;HelloWorld&quot;
</code></pre>
</li>
</ul>
<p>// &quot;Hello&quot;로 시작하는지 확인
println(text.startsWith(&quot;Hello&quot;)) // true</p>
<p>// &quot;World&quot;로 시작하는지 확인
println(text.startsWith(&quot;World&quot;)) // false</p>
</li>
</ul>
<hr>
<h3 id="📌-마치며">📌 마치며</h3>
<p>이전에 풀었던 문제 중에 <a href="https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%A0%91%EB%AF%B8%EC%82%AC%EC%9D%B8%EC%A7%80-%ED%99%95%EC%9D%B8%ED%95%98%EA%B8%B0">접미사인지 확인하는 문제</a>랑 흡사하여 endsWith()메소가 떠올라 그 반대인 startsWith()메소드를 사용해 풀었다.</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 문자열의 앞의 n글자]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%AC%B8%EC%9E%90%EC%97%B4%EC%9D%98-%EC%95%9E%EC%9D%98-n%EA%B8%80%EC%9E%90</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EB%AC%B8%EC%9E%90%EC%97%B4%EC%9D%98-%EC%95%9E%EC%9D%98-n%EA%B8%80%EC%9E%90</guid>
            <pubDate>Thu, 19 Dec 2024 04:07:39 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/c7b933ac-64d2-459b-a03d-80288e79aec6/image.png" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/cb61be93-0c87-43a0-894e-7ada7391cc6a/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String, n: Int) = my_string.substring(0, n)
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(my_string: String, n: Int): String = my_string.slice(0 until n)
}</code></pre>
<hr>
<h3 id="🖊-문제-풀이-시-알면-좋을-것">🖊 문제 풀이 시 알면 좋을 것</h3>
<ul>
<li><p>substring(0, n)</p>
<ul>
<li>문자열에서 특정 시작 인덱스(start)부터 종료 인덱스(end) 전까지 부분 문자열을 반환합니다.</li>
<li>종료 인덱스 n은 포함되지 않습니다.<pre><code class="language-kotlin">val text = &quot;Hello&quot;
println(text.substring(0, 3)) // &quot;Hel&quot;</code></pre>
</li>
</ul>
</li>
<li><p>slice(0 until n)</p>
<ul>
<li><strong>범위(Range)</strong>를 기반으로 문자열의 부분 문자열을 반환합니다.</li>
<li>종료 값 n은 포함되지 않습니다. -&gt; until일 경우에만 해당</li>
<li>until은 범위를 나타내는 키워드로, 끝 값이 포함되지 않는 범위를 생성합니다.<pre><code class="language-kotlin">val text = &quot;abcd&quot;
println(text.slice(0..2)) // &quot;abc&quot;
</code></pre>
</li>
</ul>
<p>val text = &quot;abcd&quot;
println(text.slice(0 until 2)) // &quot;ab&quot;</p>
</li>
</ul>
<br>

<h4 id="substring과-slice의-주요-차이점"><code>substring()</code>과 <code>slice()</code>의 주요 차이점</h4>
<p><strong>표현 방식</strong>
<code>substring()</code>은 직접 인덱스를 지정하며,
<code>slice()</code>는 범위를 지정합니다.</p>
<p><strong>범위 표현 가능성</strong>
slice()는 범위 표현(0..2, 0 until 3)을 활용할 수 있어 가독성이 더 좋습니다.</p>
<p><strong>선택 기준</strong>
간단한 인덱스 값만 사용할 경우: substring
범위 표현을 활용하거나 가독성을 선호할 경우: slice</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] rny_string]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-rnystring</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-rnystring</guid>
            <pubDate>Wed, 18 Dec 2024 14:37:10 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/c27d08a3-fdbf-4401-bb70-6966b340992c/image.png" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/739a0bcb-4013-4fab-80da-2385be32d1f3/image.png" alt="">
<img src="https://velog.velcdn.com/images/devel_liz/post/b5928613-318c-45a6-9f19-c2e983c7de78/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(rny_string: String) = rny_string.replace(&quot;m&quot;, &quot;rn&quot;) 
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(rnyString: String) = rnyString.replace(&quot;m&quot;, &quot;rn&quot;)
}</code></pre>
<hr>
]]></description>
        </item>
        <item>
            <title><![CDATA[[프로그래머스] 정수 부분]]></title>
            <link>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%A0%95%EC%88%98-%EB%B6%80%EB%B6%84</link>
            <guid>https://velog.io/@devel_liz/%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%A8%B8%EC%8A%A4-%EC%A0%95%EC%88%98-%EB%B6%80%EB%B6%84</guid>
            <pubDate>Wed, 18 Dec 2024 14:20:34 GMT</pubDate>
            <description><![CDATA[<h3 id="🗒-문제">🗒 문제</h3>
<p><img src="https://velog.velcdn.com/images/devel_liz/post/f297e473-601a-4f74-9ac1-08d692908e93/image.png" alt=""></p>
<hr>
<h3 id="📝-나의-문제풀이">📝 나의 문제풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(flo: Double): Int {
        return flo.toInt()
    }
}</code></pre>
<hr>
<h3 id="📝-다른-사람의-문제-풀이">📝 다른 사람의 문제 풀이</h3>
<pre><code class="language-kotlin">class Solution {
    fun solution(flo: Double): Int {
        return flo.toInt()
    }
}</code></pre>
<hr>
]]></description>
        </item>
    </channel>
</rss>