Menu
CoddyTech

Màu sắc hình ảnh

Thuộc phần Học không giám sát trong hành trình Machine Learning của Coddy. Bài học 41 trên 51.

Một người in lụa có một vài màu mực, chứ không có hàng triệu màu. k-means chọn ra một vài màu phù hợp nhất cho mỗi bức ảnh:

Hai bức ảnh hoàng hôn đặt cạnh nhau. Bên trái là ảnh gốc: bầu trời chuyển màu từ tím sang cam, mặt trời màu vàng, biển tối với ánh phản chiếu màu cam. Bên phải là cùng cảnh hoàng hôn với 4 màu phẳng

Ảnh màu có shape (hàng, cột, 3): mỗi pixel có một giá trị đỏ, xanh lá và xanh dương, mỗi giá trị nằm trong khoảng từ 0 đến 1. Một lần reshape sẽ chuyển các pixel thành dữ liệu:

Ảnh 2 x 3 gồm các pixel màu cam, vàng và xanh dương đậm, với mũi tên chỉ đến bảng gồm 6 hàng, mỗi hàng ứng với một pixel và chứa các giá trị đỏ, xanh lá và xanh dương của pixel đó

pixels = image.reshape(-1, 3)
km = KMeans(n_clusters=4, n_init=10, random_state=0).fit(pixels)
poster = km.cluster_centers_[km.labels_].reshape(image.shape)
ax.imshow(poster)

Mỗi tâm tương ứng với một màu. Dùng nhãn để lập chỉ mục các tâm sẽ gán màu của tâm cho từng điểm ảnh; thao tác reshape ghép các hàng lại thành một hình ảnh.

challenge icon

Thử thách

Trung bình

Một xưởng in poster in lụa hình hồ trên núi bằng k màu mực. Phần code khởi đầu vẽ image kích thước 40 × 60, đọc k và thiết lập biểu đồ có tiêu đề.

  1. Chuyển ảnh thành một hàng cho mỗi pixel và tìm k màu bằng k-means.
  2. Tô lại từng pixel bằng màu của tâm cụm tương ứng, rồi ghép các hàng thành ảnh.
  3. Vẽ ảnh trên ax và hiển thị.

Như hoàng hôn này với 5 màu mực:

Cảnh hoàng hôn được tô lại bằng 5 màu phẳng, có tiêu đề 5 màu mực: dải trời màu mận và hồng phấn, một dải màu cam, mặt trời màu vàng, biển xanh hải quân với những sọc màu cam

Chương trình của bạn không in ra gì: Coddy sẽ mô tả bức tranh và các màu mực. Sau đó, hãy thử các giá trị khác của k: khi nào chiếc thuyền đỏ có màu mực riêng?

Tự làm thử

import numpy as np
import matplotlib.pyplot as plt
from sklearn.cluster import KMeans


# Vẽ cảnh hồ trên núi kích thước 40 × 60: bầu trời, đỉnh núi phủ tuyết, khu rừng, mặt nước và chiếc thuyền đỏ
def paint_lake():
    image = np.zeros((40, 60, 3))
    for r in range(40):
        for c in range(60):
            if 30 <= r <= 31 and 10 <= c <= 17 - (r - 30) * 2:
                image[r, c] = [0.8, 0.15, 0.1]
            elif r >= 27:
                t = (r - 27) / 12
                image[r, c] = [0.1, 0.45 - 0.2 * t, 0.65 - 0.2 * t]
            elif r >= 21:
                image[r, c] = [0.1, 0.35 + 0.05 * (c % 3), 0.15]
            elif r >= abs(c - 34) + 4 and r < 10:
                image[r, c] = [0.95, 0.95, 0.97]
            elif r >= abs(c - 34) + 4:
                image[r, c] = [0.45, 0.42, 0.45]
            else:
                image[r, c] = [0.55 + r / 50, 0.75 + r / 120, 0.95]
    return np.round(image, 3)


# Đừng thay đổi các dòng bên dưới
image = paint_lake()
k = int(input())
fig, ax = plt.subplots()
ax.set_title(f"{k} inks")
ax.axis("off")

# Viết code của bạn bên dưới
quiz iconTự kiểm tra

Bài học này có một bài trắc nghiệm ngắn. Bắt đầu bài học để trả lời và theo dõi tiến độ.

Tất cả bài học trong Học không giám sát

Tự luyện tập: Trình biên dịch Python online