---
title: List Comprehension
tags: sprouts
slideOptions:
theme: solarized
transition: 'fade'
---
## List Comprehension!
Be pythonic
---
# Pythonic?
----
# Very python
----
## Why?
- 簡潔
- 可讀
- 入境隨俗
----
## Example
翻轉一個list
----
## C style
```python=
A = [1,2,3,4,5]
B = []
for i in range(len(A)-1, 0 ,-1):
B.append(A[i])
```
----
## Python style
```python=
A = [1,2,3,4,5]
B = A[::-1]
```
----
## Advance
將一到一百所有的偶數輸出
----
## C style
```python=
for i in range(1,101):
if i % 2 == 0:
print(i)
```
----
## Python style
```python=
# 利用list的語法特性
print(list(range(1,101))[1::2])
```
---
## List comprehension?
----
## imagine a scenario
----
## Question
輸出0~100之間,所有被2整除但不被5整除的數。
----
## Intuitive way
```python=
for i in range(101):
if i % 2 == 0 and i % 5 != 0:
print(i)
```
----
## Pythonic way
```python=
print([i for i in range(101) if i % 2 == 0 and i % 5 != 0])
```
---
## 正直善良的寫法
```python=
for i in range(101):
if i % 2 == 0 and i % 5 != 0:
print(i)
```
## 黑魔法
```python=
print([i for i in range(101) if i % 2 == 0 and i % 5 != 0])
```
----
## Definition

----
## List Comprehension
從入門到放棄,四步驟
----
## 心法
- 有list有\[\]
- 想要的在前面
- 修飾的在後面
- 源頭在中間
----
## 黑魔法解析
```python=
[i for i in range(101) if i % 2 == 0 and i % 5 != 0]
```
- 有list有\[\]
- i 是我想要的
- `if i % 2 == 0 and i % 5 != 0` 是修飾用的
- `for i in range(101)` 是源頭
----
### 當成篩子

---
## 黑魔法練習s
- 1 : 1-50所有的數
- 2 : 1-50所有5的倍數
- 3 : 1-100所有3的倍數但不是9的倍數
- 4 : 1-100所有2的次方數
----
## 黑魔法練習-1
- 1-50所有的數
```python=
[i for i in range(1,51)]
```
----
## 黑魔法練習-2
- 1-50所有5的倍數
```python=
[i for i in range(1,51) if i % 5 == 0]
```
----
## 黑魔法練習-3
- 1-100所有3的倍數但不是9的倍數
```python=
[i for i in range(1,101) if i % 3 == 0 and i % 9 != 0]
```
----
## 黑魔法練習-4
- 1-100所有2的次方數
```python=
[2**i for i in range(10) if 2**i < 101 and 2**i > 0]
```
---
## 實用黑魔法
----
### 輸入處理-DNA雜訊處理
DNA有四種含氮鹼基,分別為ATGC,但在實際上,資料往往會出現在雜訊,因此必須過濾掉不可能出現的鹼基
- Input : ATCGATGCHATGCATFC
----
## Intuitive Style
```python=
k = input()
new_k = ""
for i in k:
if i in "ATGC":
new_k+=i
```
----
## 黑魔法Style
```python=
"".join([i for i in input() if i in "ATGC"])
```
- for i in input()
- 以i遍歷input()回傳字串的每個字元
- if i in "ATGC"
- 只有在"ATGC"裡的i才會通過
- i
- Return i
---
## 進階黑魔法
如果要把錯誤用x取代呢?
----
## Intuitie Style
```python=
k = input()
new_k = ""
for i in k:
if i in "ATGC":
new_k+=i
```
----
## 黑魔法Style
else 怎麼辦???
----
## Conditional Expression
- `a if [condition] else b`
- 以下簡稱CE
----
## Example
```python=
x = 3
k = x if x % 2 == 0 else x + 1
# 若x是2的倍數回傳x否則回傳x+1
print(k)
# 4
```
----
## if else 可以巢狀
```python=
if a == b:
if b == c:
# do something
```
----
## CE也可這樣
```python=
x = 9
"A" if x % 2 == 0 else \
"B" if x % 3 == 0 else "C"
```
----
## Ans: "B"
----
## 精闢解說
- `"B" if x % 2 == 0 else ("B" if x % 3 == 0 else "C")`
- 回傳`("B" if x % 3 == 0 else "C")`
- `("B" if x % 3 == 0 else "C")`
- 回傳`"B"`
----
# 回歸正題
----
## Original
```python=
#[回傳值 迭代 遮罩]
[i for i in input() if i in "ATGC"]
```
## New
```python=
#[Expression 迭代 遮罩]
[i if i in "ATGC" else 'x' for i in input() ]
```
----
## [Expression 迭代 遮罩]
---
## 進階黑魔法練習-1
請輸出1-100之間2的倍數,若他也是3的倍數的話,請輸出原數字,否則請在數字前加上7122
----
## Solution
```python=
[int("7122"+str(i)) if i % 3 != 0 else i for i in range(1,101) if i % 2 == 0]
```
- for i in range(101)
- 迭代1~100之間的整數
- if i % 2 ==0
- 只讓2的倍數通過
- int("7122"+str(i)) if i % 3 != 0 else i
- conditional expression
----
## 進階黑魔法練習-2
----
## 改成一行版
```python=
my_list = []
for i in range(0,100):
if i % 2 == 0:
my_list.append(i)
elif i % 7 == 0:
my_list.append(-i)
else:
continue
print(mylist)
```
----
## Solution
```python=
[i if i % 2 == 0 else -i for i in range(0,100)\
if i % 2 == 0 or i % 7 == 0]
```
---
# 精益求精
----
## 脈絡
- for -> list comprehension
- if else -> list comprehension
----
## 巢狀迴圈
輸出9x9乘法表
```python=
for i in range(1,10):
for j in range(1,10):
print(i,j,i*j)
```
----
## 黑魔法
```python=
[(i,j,i*j) for i in range(1,10) for j in range(1,10))]
```
----
## 黑魔法細講
- Expression
- `(i,j,i*j)`
- Iter
- for i in range(1,10) for j in range(1,10)
- 一次
- i 跟 j 都要拿r
----
## 這不一樣啊
----
## 小魔法 (only for py3)
```python=
[print(i,j,i*j) for i in range(1,10) for j in range(1,10))]
```
----
## 小魔法解說
- 在python3,print是一個function,也就是說他屬於expression,而輸出是他的副作用,在python2,print是一個statement,因此無法丟到list comprehension內。
----
## 遮罩 x 巢狀
----
## 變形題 1
- 一樣是九九乘法表,但是對於每個數字只要輸出到n x q (q為偶數)。
----
## 老解法
```python=
for i in range(1,10):
for j in range(1,10):
if j % 2 == 0:
print(i,j,i*j)
```
----
## list comprehension一解
```python=
[print(i,j,i*j) for i in range(1,10) for j in range(2,10,2)]
```
但是我不要這個
----
## Try One
xxx要是啥呢
```python=
[print(i,j,i*j) for i in range(1,10) for j in range(1,10) xxx]
```
----
## Ans
```python=
[print(i,j,i*j) for i in range(1,10) \
for j in range(1,10) if j % 2 == 0]
```
----
## 變形題 2
- 一樣是九九乘法表,但是對於每個數字只要輸出到n x q (n小於5)。
----
## 老解法
```python=
for i in range(1,10):
if i < 5 == 0:
for j in range(1,10):
print(i,j,i*j)
```
----
## list comprehension一解
```python=
[print(i,j,i*j) for i in range(1,5) for j in range(1,10)]
```
但是我不要這個
----
## Try One
xxx 或 yyy 要是啥呢
```python=
[print(i,j,i*j) for i in range(1,10) xxx
for j in range(1,10) yyy]
```
----
## Ans
```python=
[print(i,j,i*j) for i in range(1,10) \
if i < 5 for j in range(1,10)]
```
---
## 還沒完喔XD
----
## 剛剛的引言
- 巢狀for轉換
----
## 巢狀 ?
- list comprehension可以巢狀嗎?
----
## Yape
- 因為list是個物件r
----
## 題目
- 請用list儲存一個 5 x 5 Identity矩陣
----
## I 矩陣
```python=
1 0 0 0 0
0 1 0 0 0
0 0 1 0 0
0 0 0 1 0
0 0 0 0 1
```
----
## 簡單?
- 這可是某知名外企面試題r
----
## 老解法
```python=
identity = []
for i in range(5):
row = []
for j in range(5):
row.append(1 if i == j else 0)
identity.append(row)
```
----
## 黑魔法
```python=
[[1 if i == j else 0 for i in range(5)] for j in range(5)]
```
---
## 觸類旁通
- list : 『我有comprehension,很猛!!!』
- dict : 『你有,我也有 ! ! !』
----
## Dict Comprehension
- 把 `[]` 換成 `{}`
- 從單值便成key value配對
----
## Example
```python=
{i: "hi"*i for i in range(5)}
```
----
## 衝突
- 如果有一個key對應到很多個value呢?
```python=
{0: "hi"*i for i in range(5)}
```
- last one survive
----
## 回憶過去
下列何者會有error呢?
`[{ i : i for i in range(5)} for j in range(5)]`
`{[i for i in range(5)] : "hi" for q in range(5)}`
----
## 觸類旁通(誤)
- tuple : 『把`[]`改成`()`是不是我也可以了?』
- 謎之聲 : 『拍謝,那是我~』
---
## Final Challenge
----
## Problem
Given two string a, b,
---
# Summary
----
## Pros
1. 潮
2. 快
3. 看起來很像大神<(_ _)>
----
## Cons
1. 可讀性低落
2. 腦袋很累
----
## Things Not Mentioned
- Generator comprehension
- Set comprehension
---
## Homework
- 一行解掉judge上5題
- 不限題目
- Report
- Code
- 解說
- Mailto : b04611015@csie.ntu.edu.tw
- Title : 資芽作業 『list comprehension』
---
# Q&A