簡體   English   中英

如何在golang中正確使用judy array lib?

[英]How to use judy array lib properly in golang?

在golang中,調用C庫的方式與在其他大型機動態語言(如PHP / Python / Java)中使用的方式不同,因為Golang具有不同的多任務機制,該機制不是基於OS線程的,因此調用c函數可能會導致上下文切換或線程據我了解切換。 在我的項目中,我嘗試使用Golang中的Judy Array(作為隊列工作人員)來進行一些簡單但與dict相關的大量計算,例如“選擇不同”,因此

涉及這種c lib(用於相對較高的密度計算)並盡可能減少引入的性能開銷的最佳實踐是什么?

盡管有標題,但這里的問題實際上包括兩部分:關於golang和C接口以提高效率的通用部分,以及關於對judy數組的高性能使用的特定部分。

該線程似乎總結了成本: https : //groups.google.com/forum/#!topic /golang-nuts/ RTtMsgZi88Q ,所以是的,與直接C相比,它很昂貴,因此您應該盡量減少Go的交叉點到C。

這是另外有關judy數組的建議:我以前在C / C ++代碼中使用過judy數組。 在某些地方,圖書館的界面不直觀。 並且默認情況下,它使用基於C宏的API,這使正確使用接口變得很棘手,因為編譯器無法像往常一樣提供太多幫助。

因此,我建議您首先使用C編寫測試和基准,以便您了解API及其奇怪的情況。 當為我的應用程序(相對於字符串的C ++矢量)進行基准測試時,Judy數組的速度提高了3倍,因此值得這么做。 但是將任務分為三個階段。 首先,執行您想在C中執行的操作,並確保它可以在您自己的C代碼中按預期工作。 然后擴展基本的C接口以處理您需要完成的工作,以最大程度地減少Go-> C開關的數量。 然后從Go綁定新的C接口。

如果您是從頭開始綁定庫,那么我將以盡可能最直接的方式使用cgo ,然后查看性能是否滿足您的要求。

如果不是這樣,請嘗試減少您在通常​​稱為“斑點”中進行的C調用次數。 正如您在問題中已經提到的那樣,Go進行C調用時會切換到另一個堆棧,如果您對瑣碎的函數進行大量cgo調用,這將影響性能。 因此,提高性能的一種方法是減少C調用的總數。

例如,如果您需要調用多個C函數以在Go API中實現一個操作,請考慮是否可以編寫一個小的Shim C函數來組合這些調用。

如果您要包裝的API處理了很多字符串,那么在您進行許多調用(例如:

func foo(bar string) {
    cBar := C.CString(bar)
    defer C.free(unsafe.Pointer(cBar)
    C.foo(cBar)
}

這是三個C調用。 如果您要包裝的API可以處理未終止的字符串,則此處的一種選擇是將指向該字符串的指針傳遞給包裝器,並使用在生成的_cgo_export.h定義的GoString類型。 例如,在轉到一側:

func foo(bar string) {
    C.foo_wrapper(unsafe.Pointer(&bar))
}

在C端:

#include "_cgo_export.h"
void foo_wrapper(void *ptr_to_string) {
    GoString *bar = ptr_to_string;
    foo_with_length(bar->p, bar->n);
}

只要該庫不保留foo_wrapper返回時過去的字符串數據,這應該是安全的。

可能還有其他一些優化可能會有所幫助,但是我強烈建議您一開始保持簡單,並盡力優化重要領域。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM