[Link to this article]
Http://www.cnblogs.com/hellogiser/p/double-threads-to-download-and-write.html
[Question]
Download data from the network and store the data on the hard disk. A simple practice is to download one piece and then write it to the hard disk, then download it, and then write it to the hard disk.
Disadvantage: You need to download it before writing it to the hard disk. Downloading and writing are serial operations.
Improvement: let two threads run in parallel, set the buffer, in the form of a semaphore.
Download thread. If the buffer zone is free, download the data. After the download is complete, the data in the buffer zone of the write thread is notified.
The write thread writes data as long as the buffer zone has data. After writing, it tells the download thread that the buffer zone is idle.
[Code]
C ++ Code
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 |
|
// /* Version: 1.0 Author: hellogiser Blog: http://www.cnblogs.com/hellogiser Date: 2014/7/4 */ // --------------------- API ------------------------------ // Downloads a block from Internet sequentially in each call // Return true, if the entire file is downloaded, otherwise false. Bool GetBlockFromNet (Block * out_block );
// Writes a block to hard disk Bool WriteBlockToDisk (Block * in_block );
Class Thread { Public: Thread (void (* work_func )()); ~ Thread (); Void Start (); Void Abort (); };
Class Semaphore { Public: Semaphore (int count, int max_count ); ~ Semaphore (); Void Unsignal (); Void Signal (); };
Class Mutex { Public: WaitMutex (); ReleaseMutex (); }; //----------------------------------------------------
// 1. determine to use semaphores instead of mutex to ensure parallel operations // 2. When the buffer is not satisfied and the download is not completed, the download thread runs // 3. When the buffer is not empty and the download is not completed, the storage thread runs
# Define MAX_COUNT 1000 // Buffer array, simulating cyclic queue Block g_Buffer [MAX_COUNT]; Thread g_Download (ProcA ); Thread g_Write (ProcB );
// The buffer space at the beginning is MAX_COUNT, and the entire buffer zone can be filled with downloaded data Semaphore ForDownload (MAX_COUNT, MAX_COUNT ); // No data is available in the buffer at the beginning for storage. Semaphore ForWrite (0, MAX_COUNT );
// Whether the download task is complete Bool isDone; // The downloaded data is filled in from the buffer zone. Int in_index; // Extract the stored data from the buffer zone Int out_index;
Void ProcA () { While (true) { // Obtain an idle space for data filling. ForDownload. Unsignal (); // Fill IsDone = GetBlockFromNet (g_Buffer + in_index ); // Update the index In_index = (in_index + 1) % MAX_COUNT; // Prompt that the storage thread can work ForWrite. Signal ();
// When all the tasks are downloaded, the process can be completed. If (isDone) Break; } }
Void ProcB () { While (true) { // Data is available for storage during Query ForWrite. Unsignal (); // Storage WriteBlockToDisk (g_Buffer + out_index ); // Update the index Out_index = (out_index + 1) % MAX_COUNT; // Return the free space to the buffer zone ForDownload. Signal ();
// When all the tasks are downloaded and all the data is stored in the hard disk, the process can end. If (isDone & in_index = out_index) Break; } }
Int main () { IsDone = false; In_index = 0; Out_index = 0; G_Download.Start (); G_Write.Start (); } |
[Reference]
Http://www.cnblogs.com/daniagger/archive/2012/03/23/2413764.html
Http://www.cnblogs.com/youxin/p/3586975.html
Http://blog.csdn.net/tianshuai1111/article/details/7692213
[Link to this article]
Http://www.cnblogs.com/hellogiser/p/double-threads-to-download-and-write.html