【发布时间】:2023-01-25 03:33:53
【问题描述】:
我正在尝试将其转换为并行以缩短文件的上传时间,但根据我的尝试,它并没有及时发生很大变化。 我想并排上传块,然后确认它们。我怎么能设法并行进行呢?
public static async Task UploadInBlocks
(BlobContainerClient blobContainerClient, string localFilePath, int blockSize)
{
string fileName = Path.GetFileName(localFilePath);
BlockBlobClient blobClient = blobContainerClient.GetBlockBlobClient(fileName);
FileStream fileStream = File.OpenRead(localFilePath);
ArrayList blockIDArrayList = new ArrayList();
byte[] buffer;
var bytesLeft = (fileStream.Length - fileStream.Position);
while (bytesLeft > 0)
{
if (bytesLeft >= blockSize)
{
buffer = new byte[blockSize];
await fileStream.ReadAsync(buffer, 0, blockSize);
}
else
{
buffer = new byte[bytesLeft];
await fileStream.ReadAsync(buffer, 0, Convert.ToInt32(bytesLeft));
bytesLeft = (fileStream.Length - fileStream.Position);
}
using (var stream = new MemoryStream(buffer))
{
string blockID = Convert.ToBase64String
(Encoding.UTF8.GetBytes(Guid.NewGuid().ToString()));
blockIDArrayList.Add(blockID);
await blobClient.StageBlockAsync(blockID, stream);
}
bytesLeft = (fileStream.Length - fileStream.Position);
}
string[] blockIDArray = (string[])blockIDArrayList.ToArray(typeof(string));
await blobClient.CommitBlockListAsync(blockIDArray);
}
【问题讨论】:
-
“我正在尝试将其转换为并行以缩短文件的上传时间”-它不会:上传受网络 IO 限制,但并行化只对受 CPU 限制的活动有利。由于并发网络连接和传输的开销,您更有可能以这种方式减慢速度。
-
您的
while循环运行缓慢:您在循环内分配大缓冲区:不要那样做- 我认为您的代码也不正确,因为您没有检查fileStream.ReadAsync的返回值。你不应该在循环中做new MemoryStream——也不应该做像Convert.ToBase64String (Encoding.UTF8.GetBytes(Guid.NewGuid().ToString())这样令人费解的事情——因为Guid.ToString()返回已经是URI安全的Base16数字,所以带有UTF8字节和Base64编码的rigmaore只是去混淆视听,没有任何好处。 -
此外,您的整个代码是...重新发明轮子:
GetBlockBlobClient已经可以非常有效地直接上传FileStream- 哦,您的代码中还有另一个错误:FileStream不是真正的异步除非你使用isAsyncctor。还有另一个错误:var bytesLeft = (fileStream.Length - fileStream.Position);将始终只是fileStream.Length开始 - 如果您尝试使用大于 2GB 的文件,Convert.ToInt32(bytesLeft)将失败。
标签: c# azure azure-blob-storage parallel.foreach