我有以下交易:
let insertPositionsAsync accountId timestamp (positions: PositionInfo list) : Async<Result<int, ExchangeError>> =
async {
try
use connection = getConnection location
do! connection.OpenAsync()
use writer =
connection.BeginBinaryImport(
$"COPY {accountId}.{tablePositionsName} (ts,instrument,average_price,leverage,unrealized_pnl,side,initial_margin,maintenance_margin,position_initial_margin,open_order_initial_margin,quantity,max_notional)
FROM STDIN (FORMAT BINARY)"
)
for t in positions do
do! writer.StartRowAsync() |> Async.AwaitTask
do! writer.WriteAsync(timestamp, NpgsqlDbType.Timestamp) |> Async.AwaitTask
do! writer.WriteAsync(t.Instrument.Ticker, NpgsqlDbType.Varchar) |> Async.AwaitTask
do! writer.WriteAsync(t.AveragePrice, NpgsqlDbType.Double) |> Async.AwaitTask
do! writer.WriteAsync(t.Leverage, NpgsqlDbType.Integer) |> Async.AwaitTask
do! writer.WriteAsync(t.UnrealizedPnl, NpgsqlDbType.Double) |> Async.AwaitTask
do! writer.WriteAsync(t.Side.ToString().ToLower(), NpgsqlDbType.Varchar) |> Async.AwaitTask
do! writer.WriteAsync(t.InitialMargin, NpgsqlDbType.Double) |> Async.AwaitTask
do! writer.WriteAsync(t.MaintenanceMargin, NpgsqlDbType.Double) |> Async.AwaitTask
do! writer.WriteAsync(t.PositionInitialMargin, NpgsqlDbType.Double) |> Async.AwaitTask
do! writer.WriteAsync(t.OpenOrderInitialMargin, NpgsqlDbType.Double) |> Async.AwaitTask
do! writer.WriteAsync(t.Quantity, NpgsqlDbType.Double) |> Async.AwaitTask
do! writer.WriteAsync(t.MaxNotional, NpgsqlDbType.Double) |> Async.AwaitTask
let! c = writer.CompleteAsync()
return Ok (int c)
with ex ->
error $"insertPositionsAsync {ex.Humanize()}"
return Error (ServiceException ex)
}
我的理解是回圈:
for t in positions do
do! writer.StartRowAsync() |> Async.AwaitTask
do! writer.WriteAsync(timestamp, NpgsqlDbType.Timestamp) |> Async.AwaitTask
...
let! c = writer.CompleteAsync()
發生在驅動程式中,它只是在一些本地存盤中收集資料。那么擁有所有這些異步塊是否有意義?(性能明智)。
但出于某種原因,異步 API 必須存在。我可能會錯過什么?
uj5u.com熱心網友回復:
與任何與性能相關的問題一樣,唯一有意義的答案是 衡量它并親自查看!
更一般地說,異步可以在不阻塞作業系統執行緒的情況下與資料庫進行通信。這可能會或可能不會影響性能 - 但這取決于您的程式中發生的其他事情。
如果您只有一個與資料庫通信的邏輯行程,那么在同步或異步代碼位中執行此操作沒有區別。
如果要將資料寫入資料庫,可以從多個并發寫入器執行此操作。在這種情況下,異步會有所作為,因為您可以創建更多的并發撰寫者。但我認為這可能不會有太大幫助 - 因為當您擁有過多的寫入執行緒時,資料庫可能無法更快地寫入。
一個更有趣的例子是當你在你的程式中做其他事情時。例如,如果您有一個不需要處理許多并發請求的 Web 服務器,那么使用與資料庫的異步通信是有意義的 - 因為它不會阻塞您需要處理其他 Web 請求的執行緒。
總結是,您應該衡量性能 - 但它可能取決于您的程式中發生的其他事情。我認為將單執行緒撰寫器腳本更改為異步不會有任何區別(除了增加一些小開銷的形式)。
uj5u.com熱心網友回復:
有此API的討論在這里。開頭有人說:
擁有 BeginBinaryImport 和 BeginBinaryExport 的異步版本會很有幫助,這樣它們就可以從例如 api 端點使用而不會阻塞服務器。
對于匯入,鑒于寫入發生在關閉/處理上,我猜測寫入方法不會成為異步
但是,其中一位開發人員隨后評論說:
寫也可以阻塞。所以你也需要 WriteAsync。
轉載請註明出處,本文鏈接:https://www.uj5u.com/qukuanlian/348867.html
