Hướng dẫn how to read tiff image in python - cách đọc hình ảnh tiff trong python

Đầu tiên, tôi đã tải xuống một hình ảnh TIFF thử nghiệm từ trang này có tên là

>>> import numpy
>>> imarray = numpy.array(im)
9. Sau đó, tôi đã mở với PIL như thế này:

>>> from PIL import Image
>>> im = Image.open('a_image.tif')
>>> im.show()

Điều này cho thấy hình ảnh cầu vồng. Để chuyển đổi thành một mảng numpy, nó đơn giản như:

>>> import numpy
>>> imarray = numpy.array(im)

Chúng ta có thể thấy rằng kích thước của hình ảnh và hình dạng của mảng khớp lên:

>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)

Và mảng chứa các giá trị

>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
0:

>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)

Khi bạn đã hoàn thành việc sửa đổi mảng, bạn có thể biến nó lại thành hình ảnh PIL như thế này:

>>> Image.fromarray(imarray)

TIFF định dạng tệp được sử dụng để lưu trữ các hình ảnh được raster hóa. Một thư viện có tên Thư viện trừu tượng hóa dữ liệu không gian địa lý GDAL được thiết kế đặc biệt để đọc các tệp raster này, cũng như các định dạng tệp khác, chẳng hạn như các định dạng vector. Thư viện GDAL là một phần của Quỹ không gian địa lý nguồn mở.

Để cài đặt các mô -đun cần thiết, chúng tôi có thể sử dụng các lệnh sau trong thiết bị đầu cuối của chúng tôi:

Chúng tôi yêu cầu các mô -đun matplotlib và gdal trong Python để hiển thị hình ảnh TIFF.

Approach:

  • Bước 1: Nhập mô -đun Import the module
  • Bước 2: Chúng ta có thể đếm số lượng ban nhạc. We can count how many bands.
  • Bước 3: Tìm mọi ban nhạc raster trong tệp TIFF. Find every raster band in the TIFF file.
  • Bước 4: Các ban nhạc được đọc đến các mảng numpy. The bands are read to NumPy arrays.
  • Bước 5: Trong hàm imshow () của matplotlib để hiển thị. In the imshow() function of Matplotlib to display.

Để giải thích hướng dẫn này, chúng tôi sẽ sử dụng hình ảnh sau ở định dạng TIFF:

Hướng dẫn how to read tiff image in python - cách đọc hình ảnh tiff trong python

Thực hiện từng bước:

Bước 1: Nhập các mô -đun và mở tệp. Importing the modules and opening the file.

Bước 2: Đếm tổng số băng tần. Counting the total number of bands.

Output:

Bước 3: Tìm nạp các ban nhạc Fetching the bands

Chúng tôi sử dụng GetRasterBand (INT) của GDAL để có được các ban nhạc. Điều quan trọng cần lưu ý là giá trị mà chúng ta vượt qua sẽ luôn bắt đầu bằng một (lập chỉ mục của các dải bắt đầu từ 1)

Bước 4: Đọc các ban nhạc dưới dạng mảng numpy. Reading the bands as NumPy arrays.

GDAL cung cấp phương thức readasArray () để chuyển đổi các dải đó trong các mảng numpy và trả về các mảng.

Bước 5: Vẽ các mảng bằng hàm imshow () của matplotlib. Plotting the arrays using imshow() function of matplotlib.

Để vẽ ba mảng, chúng tôi sẽ xếp chúng lên theo thứ tự.

Mã cuối cùng:

Đầu ra cuối cùng:

Hướng dẫn how to read tiff image in python - cách đọc hình ảnh tiff trong python

Sự kết luận

Trong hướng dẫn này, chúng tôi đã thảo luận về cách chúng tôi có thể trực quan hóa hình ảnh định dạng tệp TIFF bằng cách sử dụng các mô -đun matplotlib và vui mừng trong Python.


Bạn có thể nhớ từ danh sách các mô-đun phụ có trong

>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
1 rằng nó bao gồm
>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
2 là một mô-đun xử lý hình ảnh hữu ích.

Tuy nhiên,

>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
1 có xu hướng chỉ tập trung vào các thuật toán xử lý hình ảnh cơ bản nhất. Một mô-đun trẻ hơn, hình ảnh Scikit (
>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
4) chứa một số chức năng xử lý hình ảnh gần đây và phức tạp hơn.

Đối với các ứng dụng trong thế giới thực, sự kết hợp của cả hai (và/hoặc các mô-đun xử lý hình ảnh bổ sung) thường là tốt nhất.

Xử lý hình ảnh: Tổng quan chung

Mặc dù giới thiệu đầy đủ về xử lý hình ảnh tính toán nằm ngoài phạm vi của hội thảo này, bên dưới chúng tôi bao gồm một số khái niệm chính.

Một hình ảnh là một lưới thông thường của các giá trị pixel; Hình ảnh thang độ xám sẽ tương ứng với một mảng 2D của các giá trị và hình ảnh màu (RGB) Bao gồm như một kênh màu thứ 4, thường biểu thị là A A cho Alpha).

Phân đoạn

Vì hình ảnh chỉ là ma trận, hầu hết việc xử lý hình ảnh đều liên quan đến việc trích xuất thông tin từ các ma trận này. Tuy nhiên, các cảnh được chụp trong hình ảnh thường có nghĩa là chúng bao gồm (các) đối tượng nền và thường là một số tính năng khác. Do đó, việc lấy số lượng toàn bộ ma trận (như trung bình, trung bình) hiếm khi đủ.

Thay vào đó, chúng ta thường cần phân đoạn một hình ảnh thành các vùng tương ứng với tiền cảnh, có nghĩa là các đối tượng mà chúng ta đã giao thoa và nền tương ứng với mọi thứ khác.segment an image into regions corresponding to foreground, which means objects that we’re interesed in, and background which corresponds to everything else.

Phân tích

Khi một hình ảnh đã được phân đoạn, có thể cần phải xử lý thêm (chẳng hạn như chia tách các đối tượng nền trước). Giai đoạn cuối cùng trong quy trình xử lý hình ảnh là sử dụng kết quả phân đoạn để trích xuất số lượng quan tâm.

Các phân đoạn cuối cùng này cũng có thể tạo thành cơ sở của các thuật toán nâng cao như thuật toán theo dõi nếu hình ảnh là một phần của chuỗi thời gian (phim ~ phim).

Sử dụng hình ảnh scikit

Để tải bắt đầu với hình ảnh scikit, nhập mô hình con (mô-đun cốt lõi được gọi là

>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
4) quan tâm. Ví dụ: để tải một hình ảnh từ tệp, chúng tôi sẽ sử dụng mô hình con
>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
6;

import skimage.io as skio

Tải dữ liệu với >>> imarray.shape (44, 330) >>> im.size (330, 44) 7

im1         = skio.imread("SIMPLE_IMAGE.png")
imstack1    = skio.imread("FILENAME.TIF", plugin="tifffile")

Ở đây lần đầu tiên tôi hiển thị một hình ảnh đơn giản được đọc từ tệp bằng hàm

>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
8 mặc định, sau đó là một cuộc gọi thứ hai bằng cách sử dụng từ khóa
>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
9 được đặt thành
>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
0, khiến
>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
8 sử dụng mô -đun
>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
2. Điều này cho phép chúng tôi xử lý các tệp TIFF nhiều trang (nghĩa là nhiều ngăn xếp).

>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
8 Trả về một mảng numpy gồm 2 hoặc 3 chiều, tùy thuộc vào loại tệp. Sau đó, chúng tôi có thể sử dụng bất kỳ hoạt động Numpy bình thường nào mà chúng tôi mong muốn trên mảng; ví dụ.

# Lets output the mean image pixel value
print("The mean of the PNG image is :")
print( im1.mean() ) 
print("The mean of the TIFF stack (whole stack!) is:")
print( imstack1.mean() )

Hiển thị dữ liệu

Khi chúng tôi xử lý các mảng numpy, chúng tôi có thể sử dụng chức năng Imshow Matplotlib, để hiển thị một hình ảnh (giống như chúng tôi đã làm trong các bài tập matplotlib);

import matplotlib.pyplot as plt
plt.imshow(im1)
plt.show()

Ngoài ra, nhóm Scikit-Image cũng đã thêm các chức năng hiển thị hình ảnh trực tiếp vào

>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
4;

import skimage.viewer as skview
skview.ImageViewer( im1) 
skview.show()

>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
5 không tính đầy đủ như
>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
6, mặc dù các chức năng và tính năng mới được thêm vào thường xuyên.

Bắt đầu với một số xử lý dành riêng cho hình ảnh: Phân đoạn cơ bản

Hình thức phân đoạn cơ bản nhất mà chúng ta có thể áp dụng là đặt ngưỡng thủ công. Điều này giống như sử dụng giao diện ngưỡng ImageJ, và định vị thủ công vị trí ngưỡng.

Và đó là nó! Ngưỡng là đơn giản; Vì

>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
7 là một mảng numpy, dòng này sẽ tạo ra một mảng boolean được lưu trữ trong biến
>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
8, trong đó mỗi phần tử là
>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
9 nếu giá trị của
>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
7 tại vị trí tương ứng làboolean array stored in the variable
>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
8, where each element is
>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
9 if the value of
>>> imarray
array([[  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       ..., 
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246],
       [  0,   1,   2, ..., 244, 245, 246]], dtype=uint8)
7 at the corresponding location was <= 100, or
>>> Image.fromarray(imarray)

1 otherwise.

Chúng tôi có thể xác nhận điều này bằng cách xem mảng mặt nạ mới của chúng tôi;

Trên thực tế, chúng ta có thể dễ dàng phủ lên mặt nạ trên hình ảnh gốc, bằng cách sử dụng đối số từ khóa

>>> Image.fromarray(imarray)

2 thành
>>> Image.fromarray(imarray)

3, đặt tính minh bạch của hình ảnh được hiển thị;

>>> import numpy
>>> imarray = numpy.array(im)
0

Chúng tôi đã thực sự sử dụng bất kỳ chức năng xử lý hình ảnh nào; Hãy để khắc phục rằng bằng cách tự động xác định giá trị ngưỡng (thay vì sử dụng một số như

>>> Image.fromarray(imarray)

4 được lấy từ không khí mỏng!). Một trong những thuật toán ngưỡng hình ảnh phổ biến nhất, mà bạn có thể biết từ ImageJ, là thuật toán xác định ngưỡng tự động OTSU.

Để sử dụng điều này trong

>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
4, chúng tôi nhập mô hình con
>>> Image.fromarray(imarray)

6;

>>> import numpy
>>> imarray = numpy.array(im)
1

Tại thời điểm này,

>>> Image.fromarray(imarray)

7 sẽ giữ một số duy nhất, được xác định bởi thuật toán OTSU đến ngưỡng giữa những gì nó coi là nền và giá trị cường độ pixel tiền cảnh.

Sau đó chúng tôi sẽ tạo ra một mặt nạ theo cách tương tự như trước đây;

>>> import numpy
>>> imarray = numpy.array(im)
2

và có thể tiếp tục thực hiện các hoạt động xử lý hình ảnh tiếp theo của chúng tôi.

Phân tích thành phần được kết nối: >>> Image.fromarray(imarray) 8

Mặc dù có mặt nạ back-backgound nhị phân là bước đầu tiên tuyệt vời, chúng tôi thường quan tâm đến nhiều đối tượng

Trong các kịch bản như vậy, thường rất hữu ích để có thể xác định sau đó số lượng trên mỗi đối tượng, trong đó đối tượng thường được đưa ra có nghĩa là nhóm kết nối của các pixel tiền cảnh.

Cả

>>> imarray.shape
(44, 330)
>>> im.size
(330, 44)
2 và
import skimage.io as skio
0 đều bao gồm chức năng ghi nhãn thành phần kết nối được gọi là
import skimage.io as skio
1; Chúng hoạt động theo những cách rất giống nhau, nhưng hãy cẩn thận rằng có sự khác biệt tinh tế giữa.be careful that there are subtle differences between.

Về cơ bản, cả hai đều hoạt động để gán nhãn duy nhất cho từng nhóm các pixel tiền cảnh được kết nối (tức là các vùng được kết nối của

import skimage.io as skio
2 trong mảng mặt nạ).

>>> import numpy
>>> imarray = numpy.array(im)
3

Phân tích: Đo kích thước đối tượng và các đại lượng khác

Bây giờ chúng ta đã biết làm thế nào để có được mặt nạ nền tảng tương ứng với các đối tượng riêng lẻ, hãy để bắt đầu trích xuất một số đại lượng hữu ích.

Vì thực hiện các loại trích xuất thông tin này là một nhiệm vụ phổ biến như vậy,

import skimage.io as skio
0 chứa hàm tiện lợi gọi là
import skimage.io as skio
4 (có cùng tên với hàm tương đương MATLAB trong hộp công cụ xử lý hình ảnh bổ sung MATLAB MATLAB).

import skimage.io as skio
4 tạo ra một danh sách các đối tượng
import skimage.io as skio
6 (bộ sưu tập thuộc tính), sau đó chúng ta có thể kiểm tra. Ví dụ

>>> import numpy
>>> imarray = numpy.array(im)
4

Chúng tôi cũng có thể thu thập các thuộc tính cụ thể (để vẽ, ví dụ:), bằng cách sử dụng danh sách hiểu (hoặc A cho vòng lặp);

>>> import numpy
>>> imarray = numpy.array(im)
5

Nếu tài sản mà chúng tôi quan tâm không có mặt trong đầu ra của

import skimage.io as skio
7, chúng tôi cũng có thể tự mình tính toán chức năng của mình. Có một số cách tương đối đơn giản để thực hiện việc này, cụ thể là sử dụng chức năng tiện ích như ____ 22 22
import skimage.io as skio
9 hoặc thay vào đó là một danh sách hiểu hoặc cho vòng lặp qua các giá trị nhãn. Ví dụ: chúng ta có thể nhận các khu vực đối tượng bằng cách sử dụng

>>> import numpy
>>> imarray = numpy.array(im)
6

hoặc tương đương

>>> import numpy
>>> imarray = numpy.array(im)
7

Phân khúc bổ sung: Biến đổi đầu nguồn

Thông thường các đối tượng thực tế được biểu thị trong hình ảnh của chúng tôi chạm (hoặc xuất hiện), khiến chúng được dán nhãn bởi cùng một nhãn trong quá trình phân tích thành phần được kết nối.

Trong các loại Scarios này, có thể có thể sử dụng một thuật toán được gọi là biến đổi đầu nguồn để phân chia các đối tượng chạm vào.

Tuy nhiên, lưu ý rằng chiến thắng này đã giải quyết tất cả các tình huống với các đối tượng chạm vào, và trong một số tình huống, các đối tượng chỉ đơn giản là giành được sự giải quyết, trong khi ở những người khác, một chiến lược khác nhau để chia cho đối tượng có thể cần thiết.

Để áp dụng biến đổi đầu nguồn, hãy nhập mô hình con

im1         = skio.imread("SIMPLE_IMAGE.png")
imstack1    = skio.imread("FILENAME.TIF", plugin="tifffile")
0,

>>> import numpy
>>> imarray = numpy.array(im)
8

Exericse: Đếm và đo lường Blobs ”

Bây giờ, chúng tôi đã bao gồm một số kỹ thuật xử lý hình ảnh cốt lõi, hãy để chúng đưa chúng vào thực tế trong bài tập kéo dài này.

Tải xuống tệp hình ảnh từ đây: http://www.proteinatlas.org/images/46290/964_h7_1_blue_red_green.jpg (từ www.proteinatlas.org)

GHI CHÚ

Dữ liệu này được lưu dưới dạng JPG, một định dạng hình ảnh nén sử dụng nén mất; nhưng hãy nhớ -lossy compression; but remember -

Giữ dữ liệu thô của bạn ở định dạng không nén..

(hoặc nén không mất mát như PNG khi thích hợp).

  • Sử dụng phương pháp phân đoạn được nêu ở trên để đếm số lượng hạt nhân (đốm xanh lớn màu xanh lá cây) trong hình ảnh
  • Cũng tạo một biểu đồ phân phối kích thước của chúng
  • Hãy thử và xem liệu bạn có thể tìm hiểu làm thế nào để không bao gồm các hạt nhân chạm vào các cạnh

Thưởng

  • Như thường lệ, phân khúc của bạn rất có thể sẽ không khớp 100% mô hình tinh thần của bạn về cách nó trông như thế nào vì dữ liệu không hoàn hảo! Xem nếu bạn có thể tìm thấy bộ lọc hoặc kết hợp các bộ lọc giúp tăng cường phân đoạn cuối cùng của bạn.
  • Đếm số lượng điểm tối bên trong mỗi ô và vẽ sơ đồ phân phối số điểm tối.
  • Sử dụng một giới hạn trên kích thước tối thiểu hoặc một số kỹ thuật khác để chỉ bao gồm các điểm tối trên kích thước 3x3 pixel (vì các điểm tối nhỏ hơn có thể là nhiễu).

Bài tập bổ sung?

Kỹ thuật xử lý hình ảnh là cụ thể cho nhiệm vụ được giải quyết; Bài tập trước, trong khi có thể được một số bạn quan tâm, sẽ không có nghĩa là hữu ích cho tất cả mọi người.

Thay vì làm việc trên các bài tập bổ sung, vui lòng thử và thực hiện xử lý hình ảnh hữu ích cho bạn bằng cách sử dụng dữ liệu của riêng bạn (hoặc tìm dữ liệu tương tự trực tuyến).