Ho tentato di implementare unoe WriteAsync
e e, data la scarsità dello documentation, sto faticando a capire come farlo correttamente. Specificamente, rispetto alla posizione del cursore del flusso. Una domanda simile è stata richiesta here e here riguardo alla vecchia funzione BeginRead
. La documentazione relativa a tale funzione sembrava indicare che BeginRead
non dovrebbe essere richiamato fino a quando non sono state completate tutte le operazioni asincrone in sospeso.Are Stream.ReadAsync e Stream.WriteAsync suppongono di alterare la posizione del cursore in modo sincrono prima di tornare o al termine dell'operazione?
Dato che BeginRead
è ora deprecatono longer recommended for new development e Stream
è probabilmente stato significativamente alterato per implementare le nuove funzioni asincrone, le cose sono ancora una volta poco chiari. (MODIFICA: Solitamente questo tipo di avvertimento significa che le nuove funzioni sono implementate direttamente e le vecchie funzioni chiamano quelle nuove e sono ancora lì solo per compatibilità all'indietro, ma sembra che non sia proprio il caso qui).
I ReadAsync
e WriteAsync
funzioni sono definite in modo tale che non prendono posizione flusso di lettura/scrittura desiderata come loro Win32counterparts fare (una scelta di design molto scarsa a mio parere), ma invece fare affidamento sulla posizione corrente detenuta da l'implementazione del flusso. Tale situazione è soddisfacente se una delle due condizioni:
ReadAsync
eWriteAsync
deve afferrare la posizione attuale del cursore per uso dall'operazione e aggiornarlo come se l'operazione è stata completata (o non aggiorna affatto) prima che ritorninoTask
o- Nessuna chiamata a
ReadAsync
oWriteAsync
può essere effettuata fino a quando tutte le precedenti chiamate asincrone sono state completate.
Al di fuori di queste due condizioni, il chiamante non può mai essere sicuri della posizione di lettura o scrittura si verifica a causa in attesa di operazioni asincrone potrebbe alterare la posizione del flusso tra qualsiasi Seek
e chiamare per ReadAsync
o WriteAsync
. Nessuna di queste condizioni è documentata come un requisito, quindi sono lasciato a chiedermi come dovrebbe funzionare.
mio test strutturale sembra indicare che, almeno per la versione FileStream
del Stream
, il flusso di posizione aggiorna in modo asincrono, il che sembrerebbe indicare che la seconda condizione (una sola in attesa di operazione consentita) è ancora quello che è richiesto, ma sembra una seria limitazione (di certo preclude qualsiasi tipo di implementazione di scatter-gather interna).
Qualcuno può fornire qualsiasi tipo di informazione autorevole se la precedente limitazione BeginRead
si applica ancora allo ReadAsync
oppure no?
Penso che la logica alla base del progetto sia che un flusso è, per sua natura, non thread-safe; quindi non ha senso accedervi mentre è in corso un'operazione asincrona (solo perché l'operazione è asincrona, permettendo al tuo codice di attendere con garbo nello streaming lettura/scrittura senza bloccare, non significa che sia una buona idea giocare con lo stream da un altro thread mentre l'operazione è in corso). – Cameron
Dato che 'ReadAsync' leggerà un numero sconosciuto di byte, come potrebbe eventualmente aggiornare accuratamente la posizione prima che l'operazione sia completata? –
I/O simultanei, anche se avviati sequenzialmente, possono causare il richiamo della chiamata in modo concorrente. Questa è una condizione di competizione per la maggior parte delle implementazioni di stream. Quindi questo non è permesso in generale. – usr