2012年11月27日 星期二

Java 數字溢位時的處理

做個小記錄~
目前打算模仿 ConcurrentHashMap 在實作 OCC 的方法,去做出不需要 Exclusive Lock 的 Concurrent Control
所以會需要一直對某個數字做遞增~
但是不太確定 JVM 對於數字遞增到最大值以後到底會如何處理,因此稍微查了一下。

2012年11月13日 星期二

ImageIO 輸出圖檔時的顏色問題

今天發現一個 BUG,當圖片用 PNG 檔時,用程式產生的縮圖顏色會很詭異
經過了一些簡單的測試,初步發現顏色有問題的都是背景有大量白色的圖片
後來就找到 [1] 的討論,其中回應是說因為 JPEG 本身沒有透明度設定
因此當遇到圖片是非 JPEG,但輸出檔案時卻指定為 JPEG,這時產生的檔案就會有問題。

要解決這個問題,一種是用 ImageIO 輸出時不要改變輸出的檔案類型,沒有轉檔就不會有圖片不相容的問題 XD
另一種就是參考 [1] 討論中的各種方法,基本上好像概念都是對透明的東西全部轉換成白色或者某個指定的顏色。

參考資料:
1、Converting transparent gif / png to jpeg using java

2012年11月8日 星期四

提昇 MongoDB 的讀取效能

在我們專案裡面有個 MongoDB 的資料庫,在測試時發現裡面的 19 萬筆資料全倒出來時
花費的時間相當可觀,平均大約是 10~15 秒左右!
但 19 萬筆資料並不算是很龐大的資料,理論上不應該出現這種結果
因此花了些時間查詢有沒有方法可以提昇效率~。

邊查邊測了大概兩天,其實沒查到什麼方法
倒是有發現如果直接在 MongoDB 的 shell 上面輸入同樣的語法時,shell 只要花不到 3 秒就可以取完所有的 document。

從 Thread 接受回傳值:Callable

一般使用 Thread 都會使用 Runnable,但是 Runnable 預設要實作的 run() 回傳值是 void,並且 run 也無法回應 Exception
當外邊有 Thread 需要等其他 Thread 執行完畢後的結果時,常常只能另外寫一個 get() 函式去判斷並取值。
不過在 Java 1.5.0 版開始,額外增加了 Callable,可以允許 Thread 回傳值了。

基本的範例可以直接參考 [1] 的範例~
簡單來說,在宣告 Callable 時,就要先宣告回傳值,然後用 Future 去綁對應的 Callable
最後把 Future 餵給 Thread 去執行~就可以透過 Future.get() 函式取得 Callable 執行完畢後的回傳值。

2012年11月5日 星期一

Thread.join()

之前搞不太清楚 Thread 裡面的 join() 函式的用途,最近終於搞清楚了~
一般來說因為 Thread 是非同步的執行,因此當新的 Thread 被產生出來之後,跟原本的 Thread 的執行順序就不保證了
但有時我們還是會想要等某個 Thread 執行完畢以後,現在的 Thread 再繼續執行
這時就可以利用 join() 函式去等待。

2012年11月1日 星期四

測試 MongoDB 的效能

設定了一個情境,假設我有 100 萬個檔名不同的檔案,隨機放在以下八個資料夾

/user_c/
/user_c/application/
/user_a/log/user_c/
/user_a/log/webserver/
/user_b/
/user_b/application/
/user_b/log/
/user_b/log/webserver/

那麼當我想要知道 /user_c/ 這個資料夾有哪些檔案和資料夾時,MongoDB 可以多快幫我找出來?

用 Java 存取 MongoDB

要透過 Java 連接、插入和讀取 MongoDB,方法其實在官方的文件 [1] 中寫得蠻清楚的~
以下直接轉貼官方的範例。

連接 MongoDB
Mongo m = new Mongo();
DB db = m.getDB( "mydb" );
DBCollection coll = db.getCollection("testCollection");
在產生 Mongo 的實體時,如果沒有輸入任何參數,會自動使用 MongoDB 預設的 localhost:27017 來連接。
有需要的時候可以自行指定位址和連接埠,另外也可以用 ServerAddress 的方式來表達多個 MongoDB 的位址(用於 sharding)。

初始化 Mongo 的實體之後,可以使用 getDB() 來指定要使用的資料庫名稱,然後再使用 getCollection() 選定目前要存取的集合名稱。

2012年10月30日 星期二

在 Windows 初次安裝、使用 MongoDB

這篇是簡易記錄文~記錄一下在 Windows 上安裝和小小測試 MongoDB 的過程。

MongoDB 的安裝和使用方法,在官方網站的文件上其實有說蠻多的,可以參考 [1-2]。

在 Windows 上安裝 MongoDB

在下載好 MongoDB 之後,它會是個壓縮檔,解壓縮之後放在某個自己想放的位置
以官網的教學建議是放在 C:\mongodb,不過放在哪都無所謂~自己方便就好。

PS. 為了方便起見,後面都會以 C:\mongodb 當做是 MongoDB 的所在路徑。

接著要先建立 MongoDB 放資料庫的位置,預設會放在 C:\data\db 這個目錄
因此要用檔案總管或其他方式,把這個目錄建立起來,否則啟動 MongoDB 時它會告知找不到路徑而自行關閉。
如果不想要放在這個目錄,要用以下指令去更改路徑,這裡直接用官網的範例,即要改到 D:\test\mongodb\data:
C:\mongodb\bin\mongod.exe --dbpath d:\test\mongodb\data
如果路徑包含空白,例如路徑是「D:\test\mongo db data」的話,可以用雙引號把完整路徑包起來,例如:
C:\mongodb\bin\mongod.exe --dbpath "d:\test\mongo db data"
基本上這樣就完成 MongoDB 的安裝了(咦?!)
嚴格來說它根本也沒什麼好安裝的,就是壓縮檔抓下來解壓縮就好 XD。

2012年10月29日 星期一

MongoDB Concurrency

MongoDB 的 concurrency 的資料,感覺好像比較難查....

Global Write Lock / Yield Lock (Locking-With-Yield)

首先是關於在 MongoDB v2.0 以前(含 2.0)的版本,MongoDB 具有兩個特性:global write lock 和 yielding lock。
詳情可以參考看看 [2-4],以下說明大略是出自 [2] 的說法~。