2009-10-30 42 views
8

我正在使用大約20000 x 20000像素的1gb大型tiff圖像。我需要從圖像中隨機抽取幾塊圖像(大約300x300像素)。高效TIFF瓷磚提取C++

我嘗試以下解決方案:

  • 的libtiff(唯一的低級別庫,我能找到)提供TIFFReadline(),但是,這意味着在讀圍繞19700 unnecesary像素。

  • 我實現了我自己的tiff閱讀器,它可以從圖像中提取圖塊而不讀取不需要的像素。我預計它會更快,但是爲每塊瓷磚做一個seekg使其非常緩慢。我也嘗試讀取緩衝區中所有包含我的圖塊的文件的行,然後從緩衝區中提取圖塊,但結果差不多。

我希望收到可以改進我的瓷磚提取工具的建議!

一切是值得歡迎的,也許你可以提出更有效的庫我可以使用,關於C/C++的I/O,一些更高層次的滿足我的需求戰略的一些技巧等

問候, 胡安

+0

我們可以假設它們是未壓縮的嗎? – 2009-10-30 17:30:40

+0

而且數據是在掃描線中組織的? – 2009-10-30 17:44:03

+0

是,數據是未壓縮和組織最traditinal方式: 一號線2號線 3號線 ... – Juan 2009-11-02 12:47:32

回答

2
+0

我目前正在測試這個選項。感謝您的回覆。 – Juan 2009-11-13 14:52:49

+0

在64位操作系統上有趣。大的tiff文件很容易超過32位的邊界。在我的XP上,我有讀取400MByte及以上位圖的問題,因爲'虛擬內存'碎片化。即:即使使用2 GB的免費(!)RAM,我也無法找到400 MB的連續內存空間塊。 – Adriaan 2010-01-14 22:05:20

3

[主要編輯10年1月14日]

我還是有點貴的瓷磚提起,迷茫時,TIFF是不是平鋪。

我確實使用平鋪/金字塔TIFF圖像。我創建了那些VIPS

vips im_vips2tiff source_image output_image.tif:none,tile:256x256,pyramid 

我認爲你可以這樣做:

vips im_vips2tiff source_image output_image.tif:none,tile:256x256,flat 

你可能想用瓷磚大小的實驗。然後你可以使用TIFFReadEncodedTile進行閱讀。

如果您需要放大/縮小,使用金字塔tiff的多分辨率存儲速度要快得多。您可能還想用它來製作一幅粗略的圖像,接下來是詳細的圖片。

切換到(大小適中的)平鋪存儲(這會爲隨機訪問帶來巨大的性能改進!),您的瓶頸將是磁盤io。如果按順序讀取,文件讀取速度會更快。這裏的映射可能是解決方案。

一些有用的鏈接:

VIPS IIPImage LibTiff.NET stackoverflow VIPS是一種圖像處理庫,可以做更多的不僅僅是讀/寫。它有自己的,非常有效的內部格式。它有一個很好的算法文檔。首先,它從文件系統中分離處理,從而允許緩存切片。

IIPImage是一個多變焦網絡服務器/瀏覽器庫。我發現該文檔是多分辨率成像信息的非常好的來源(如谷歌地圖)

此頁面上的其他解決方案使用mmap,僅對'小'文件有效。我經常碰到32位的邊界。通常情況下,分配1 GB的內存將在32位操作系統(安裝4 GB內存)上失敗,這是因爲即使在運行一個或兩個應用程序後,虛擬內存也會分裂。仍然有足夠的內存來緩存部分或整個圖像。更多的內存=更多的性能。

+0

TIFF可以平鋪或具有數據條。這是管理大圖像創建和讀取的唯一方法。 – WhoCares 2018-01-12 13:04:02

0

我做了類似的事情來處理一個任意大的TARGA(TGA)格式文件。 使這種文件變得簡單的事情是圖像沒有被壓縮。您可以計算圖像內任意像素的位置,並通過簡單的查找來找到它。如果您可以選擇指定圖像編碼,則可以考慮使用targa格式。

如果沒有TIFF格式的種類很多。如果他們已經經歷了支持所有不同格式的痛苦,那麼你可能想要使用一個庫。

2

謝謝大家的回覆。

實際上,需要改變瓷磚的方式,允許我以順序的方式從硬盤中的文件中提取瓷磚,而不是隨機的方式。這使我可以將文件的一部分加載到內存中,並從那裏提取切片。

效率增益巨大。否則,如果你需要隨機訪問一個文件,mmap是一個很好的交易。

問候, 胡安

-1

你得到一個特定的錯誤消息?根據您使用該命令行的方式,您可能已經加入了自己的文件。

如果這不是問題,請嘗試使用imagemagick而不是vips(如果它是一個選項)。