2012-04-19 9 views
0

これを実装する前に、これが未定義の動作または競合状態につながるかどうか確認したいと思います。信号とスロットを使用したファイルのインクリメンタルアップロード

ファイルをアップロードするときは、ブロック単位で行う必要があります。私は並行して5ブロックをアップロードしたい、彼らはすべて同じファイルから自分のデータを取得します。これは次のようになります。

char *currentDataChunk; 
int currentDataChunkSize; 

connect(_blobStorageProvider, SIGNAL(putBlockSucceded(int)), this, SLOT(finalizeAndUploadNextBlock(int))); 

int parallelUploads = ((_item->size()/MAX_BLOCK_SIZE) >= MAX_PARALLEL_BLOCKUPLOADS) ? MAX_PARALLEL_BLOCKUPLOADS : (_item->size()/MAX_BLOCK_SIZE); 

_latestProcessedBlockId = (parallelUploads - 1); 

for(int i = 0; i < parallelUploads; i++) { 

    currentDataChunkSize = _item->read(currentDataChunk, MAX_BLOCK_SIZE); 

    ... 

    uploader->putBlock(_container, _blobName, currentDataChunk, i); 
} 

uploaderのputBlock関数では、呼び出したQNetworkAccessManagerを呼び出します。それが完了したら、ブロックされたブロックのどれかがわかるように、失敗したか、succededか、取り消されたか、blockIdと一緒にシグナルを返します。

void BigBlobUploader::finalizeAndUploadNextBlock(int blockId) { 

    // FINALIZE BY ADDING SUCCESSFUL BLOCK TO FUTURE BLOCKLIST 
    QByteArray temp; 

    for(int i = 0; i != sizeof(blockId); i++) { 
     temp.append((char)(blockId >> (i * 8))); 
    } 

    _uploadedBlockIds.insert(blockId, QString(temp.toBase64())); 
    this->uploadNextBlock(); 
} 

void BigBlobUploader::uploadNextBlock() { 

    char *newDataChunk; 
    int newDataChunkSize = _item->read(newDataChunk, MAX_BLOCK_SIZE); 
    ... 
    _latestProcessedBlockId++; 
    uploader->putBlock(_container, _blobName, newDataChunk, _latestProcessedBlockId); 
} 
私の計画は今率を高める、このブロックは(このブロブを完成させるためにブロックリストを置くことができるように、リストに入れて)アップロードされたことにご注意くださいスロットにこれらの信号を取り出すことです

(5から始まります)、新しいデータチャンクを取り出して、プロセス全体をやり直します。

私の問題は、そのうち2つが同時に正確に終了するとどうなりますか?私はここでスレッドを扱っていませんが、HTTPリクエストはデフォルトでスレッドされているので、ここでは何がありますか?シグナルはキューに入れられていますか(またはQueuedConnectionを使用すべきですか)?スロットを並行して呼び出すことはできますか?これを行うより良い方法はありますか?

答えて

-1

QNetworkAccessManagerに慣れていません。しかし、一般的に競争条件に対処するには、ロックを使用してください。通常、C#でロックを使用する方法は、lockキーワードを利用しています。ような何か:また

private object lockingObject = new object(); 

In a method: 

lock 
{ 
       // If a thread acquires a lock, another thread is blocked here until the lock is released. 
} 

、あなたはより多くの情報のためhttp://msdn.microsoft.com/en-us/library/c5kehkcz(v=vs.100).aspxを参照することができます。

最高のお礼、

Ming Xu。

+0

このスロットには別のスレッドがアクセスすることはありません。これは、qt/C++のシグナル/スロットメカニズムでどのように動作するのかを知る必要があります。 – chikuba

0

ご迷惑をおかけして申し訳ございませんが、このスレッドにWindows Azureタグを追加してから.NETを使用していると仮定しました。私はWindows Azureによく似ていますが、Qtに関する私の理解は限られています。ただし、他の同時シナリオでは信号/スロットを使用することと変わりありません。この文書は、http://qt-project.org/doc/qt-4.8/signalsandslots.htmlに役立ちます。

最高のお礼、

Ming Xu。