How iphone iOS uses Gcd,block

Source: Internet
Author: User
Tags gcd

How iphone iOS uses Gcd,block: http://blog.sina.com.cn/s/blog_45e2b66c01010dhd.html

1. GCD's dispatch queue

Http://www.cnblogs.com/scorpiozj/archive/2011/07/25/2116459.html

2. The magic of GCD in iOS

http://blog.csdn.net/favormm/article/details/6453260

3. Officially, it's a lot of content.

http://developer.apple.com/library/ios/#documentation/performance/reference/gcd_libdispatch_ref/reference/reference.html

http://developer.apple.com/library/ios/#documentation/general/conceptual/concurrencyprogrammingguide/ Operationqueues/operationqueues.html#//apple_ref/doc/uid/tp40008091-ch102-sw1

4. Detailed iOS Development application concurrency dispatch Queues

Http://mobile.51cto.com/iphone-283323.htm

5. Stanford University's lecture notes on GCD

Http://www.stanford.edu/class/cs193p/cgi-bin/drupal/system/files/lectures/Lecture 13_0.pdf

GCD is actually a simple version of multithreading. GCD and block are brothers, so learn gcd before need to understand block, do not know also nothing, look at the code to understand.

iOS seed GCD

GCD is closely connected to block, so it's best to get to know the block (see my previous collection of articles). GCD is a C level function, which means that it also provides a C function pointer as a parameter that facilitates the C programmer.

Let's start with the use of GCD:

Dispatch_async (dispatch_queue_t queue, dispatch_block_t block);

Async indicates that the block represents the thing you want to do asynchronously, and the queue is the one who handles the task. (in addition to async and Sync,delay, this article takes async as an example).

Multithreading is used in programs because the program often needs to read the data and then update the UI. For a good user experience, reading data will tend to run in the background to avoid blocking the main thread. There are three kinds of queue to deal with in GCD.

1. Main Queue:

As the name implies, it runs on the main thread and is obtained by Dispatch_get_main_queue. UI related to using the main Queue.

2.Serial Quque (Private dispatch queue, where dispatch_queue_t is one)

Each time you run a task, you can add multiple, execution order FIFO. Usually refers to a programmer's generation, such as:

NSDate *da = [NSDate Date]; NSString *dastr = [da description];

const char *queuename = [Dastr utf8string];
dispatch_queue_t myqueue = dispatch_queue_create (QueueName, NULL);

3. Concurrent Queue (Global dispatch queue, where dispatch_time_t is one):

You can run multiple tasks at the same time, each of which depends on the order in which the queue is joined, and on the sequence in which it ends. obtained using Dispatch_get_global_queue.

So we can get a general idea of the framework using GCD:

Dispatch_async (getdataqueue,^{//Get the data, get a group, refresh the UI. DISPATCH_AYSNC (mainqueue,^{//ui update needs to be done in the main thread};})

In iOS, blocks is an object that encapsulates a piece of code that can be executed at any time. Blocks can be used as a function parameter or as a return value of a function, and it can have an input parameter or return value itself. It is similar to a traditional function pointer, but differs: blocks is inline , and it is read-only to local variables.

Ios4 has directly supported blocks,

definition of Blocks:

Int (^multiply) (int, int) = ^ (int num1, int num2) {return NUM1 * num2;};

Defines a multiply blocks object that has two int parameters and returns an int. The right side of the equation is the concrete implementation of blocks, note {}blocks in the body;.

Blocks can access local variables, but cannot be modified.

int multiplier = 7;

Int (^myblock) (int) = ^ (int num) {

Multiplier ++;// Compile error

return num * multiplier;

};

Add keyword if you want to modify: __block

__block int multiplier = 7;

Int (^myblock) (int) = ^ (int num) {

Multiplier ++;//, that's it.

return num * multiplier;

};

As a function parameter, blocks replaces the callback function or delegate in some sense. When a function is called, it is assumed that an event is triggered, and then the contents of the blocks run. This facilitates the integration of code and reading, you do not need to go everywhere to implement the delegation method.

There are already a lot of support blocks parameters in the system API.

· Completion handlers

· Notification handlers

· Error handlers

· Enumeration

· View Animation and Transitions

· Sorting


Function prototypes

Dispatch_async (dispatch_queue_t queue, dispatch_block_t block);

Async indicates that it runs asynchronously. (in addition to async and Sync,delay, this article takes async as an example).

The queue is where you give the task to someone who handles it.

Block stands for what you're going to do.

There are three types of queue

Main: tasks execute serially on your application ' s Main thread Concurrent: tasks start executing in FIFO Order, but can run concurrently. Serial: tasks execute one at a time in FIFO order

    • (1) Serial Queues (serial queue) is also known as the private Dispatch queue (privately), which is typically used to synchronize access to specific resources. We can create as many serial queues as we need, and each serial queue is concurrent.
    • (2) Parallel queue, also known as global dispatch queue. While parallel queues can perform multiple tasks concurrently, the order in which the tasks start executing is the same as the order in which they join the queue. We can't do this ourselves. Create a parallel dispatch queue. There are only three available global concurrent queues.
    • (3) The main dispatch queue is a globally available serial queue that performs tasks on the main thread of the program. This queue's tasks are alternately executed with the event source that the application's main loop (run loop) is to execute. Because it runs in the main thread of the application, the main queue is often used as a synchronization point for the application

Look at a piece of code first

View Plain

    1. @interface Uiimageview (dispatchload)
    2. -(void) Setimagefromurl: (nsstring*) urlstring;
    3. -(void) Setimagefromurl: (nsstring*) urlstring
    4. Completion: (void (^) (void)) completion;
    5. @end

View Plain

  1. #import "Uiimageview+dispatchload.h"
  2. @implementation Uiimageview (dispatchload)
  3. -(void) Setimagefromurl: (nsstring*) urlstring {
  4. [Self setimagefromurl:urlstring completion:null];
  5. }
  6. -(void) Setimagefromurl: (nsstring*) urlstring
  7. Completion: (void (^) (void)) Completion {
  8. Dispatch_async (Dispatch_get_global_queue (dispatch_queue_priority_default, 0), ^{
  9. NSLog (@ "Starting:%@", urlstring);
  10. UIImage *avatarimage = nil;
  11. Nsurl *url = [Nsurl urlwithstring:urlstring];
  12. NSData *responsedata = [NSData Datawithcontentsofurl:url];
  13. Avatarimage = [UIImage imagewithdata:responsedata];
  14. NSLog (@ "Finishing:%@", urlstring);
  15. if (avatarimage) {
  16. Dispatch_async (Dispatch_get_main_queue (), ^{
  17. Self.image = Avatarimage;
  18. });
  19. Dispatch_async (Dispatch_get_main_queue (), completion);
  20. }
  21. else {
  22. NSLog (@ "--Impossible Download:%@", urlstring);
  23. }
  24. });
  25. }
  26. @end

The above code is mainly implemented, the image is loaded asynchronously.

Break it down:

1> Add to GCD queue

View Plain

    1. Dispatch_async (Dispatch_get_global_queue (dispatch_queue_priority_default, 0), ^{

This code is implemented primarily to add the image loading block to the queue queues,

View Plain

    1. Dispatch_get_global_queue (Dispatch_queue_priority_default, 0),

This is the acquisition of a global parallel queue (dispatch queue) with only 3 system queues.

2> loads the image. This filter.

3> notify or update the main thread

View Plain

    1. Dispatch_async (Dispatch_get_main_queue (), ^{
    2. Self.image = Avatarimage;
    3. });
    4. Dispatch_async (Dispatch_get_main_queue (), completion);

"One of the advantages of block is that it can use variables outside its own domain, such as a block that can read the variable value of its parent scope, which is copied into the data structure of the block heap. When a block is added to the dispatch queue, these values are usually read-only. ”

The update UI can only be implemented in the main thread, so the main thread function is called completion

This completes the process of loading the image asynchronously.

Serial queues are useful when you want tasks to execute in a particular order. A serial queue performs only one task at a time. We can use serial queues instead of locks to protect shared data. Unlike locks, a serial queue guarantees that the task executes in a predictable order.

Unlike concurrent queues, we create and manage serial queues on our own, and can create any number of serial queues. When we create a serial queue, it should be for some purpose, such as securing resources, or synchronizing certain key behaviors of the application.

The following code describes how to create a custom serial queue, the function dispath_queue_create requires two parameters, the queue's name, and the queue's properties. Debugger and performance tools display the name of the queue help us to track how the task executes, the properties of the queue are reserved for future use, should be null

    1. dispatch_queue_t queue;
    2. Queue = Dispatch_queue_create ("Com.example.MyQueue", NULL);

In addition to the custom queues that you create, the system automatically creates a serial queue for me and binds it to the main thread of the application. Here's how to get it.

Post a few pieces of Stanford's code for GCD, which shows how to fix the error, which is used as a serial queue

1. This is the original code.

View Plain

    1. -(void) Viewwillappear: (BOOL) animated
    2. {
    3. NSData *imagedata = [Flickrfetcher imagedataforphotowithurlstring:photo. URL];
    4. UIImage *image = [UIImage imagewithdata:imagedata];
    5. Self.imageView.image = image;
    6. Self.imageView.frame = CGRectMake (0, 0, image.size.width, image.size.height);
    7. Self.scrollView.contentSize = image.size;
    8. }

2. This is the code using GCDD, there are 3 errors

View Plain

  1. -(void) Viewwillappear: (BOOL) animated
  2. {
  3. dispatch_queue_t downloadqueue = dispatch_queue_create ("Flickr downloader", NULL);
  4. Dispatch_async (Downloadqueue, ^{
  5. NSData *imagedata = [Flickrfetcher imagedataforphotowithurlstring:photo. URL];
  6. UIImage *image = [UIImage imagewithdata:imagedata];
  7. Self.imageView.image = image;
  8. Self.imageView.frame = CGRectMake (0, 0, image.size.width, image.size.height);
  9. Self.scrollView.contentSize = image.size;
  10. });
  11. }

3. First error, UI update can only be problem! in the main thread UIKit calls can only happen in the main thread!

Corrected as follows:

View Plain

  1. -(void) Viewwillappear: (BOOL) animated
  2. {
  3. dispatch_queue_t downloadqueue = dispatch_queue_create ("Flickr downloader", NULL);
  4. Dispatch_async (Downloadqueue, ^{
  5. NSData *imagedata = [Flickrfetcher imagedataforphotowithurlstring:photo. URL];
  6. Dispatch_async (Dispatch_get_main_queue (), ^{
  7. UIImage *image = [UIImage imagewithdata:imagedata];
  8. Self.imageView.image = image;
  9. Self.imageView.frame = CGRectMake (0, 0, image.size.width, image.size.height);
  10. Self.scrollView.contentSize = image.size;
  11. });
  12. }); }

4. The second error, Nsmanagedobjectcontext, is not thread-safe, and accessing member variables in GCD is dangerous

problem! Nsmanagedobjectcontext is not thread safe,

So we can ' t call photo. URL in Downloadqueue ' s t

Corrected as follows:

View Plain

  1. -(void) Viewwillappear: (BOOL) animated
  2. {
  3. NSString *url = photo. URL;
  4. dispatch_queue_t downloadqueue = dispatch_queue_create ("Flickr downloader", NULL);
  5. Dispatch_async (Downloadqueue, ^{
  6. NSData *imagedata = [Flickrfetcher Imagedataforphotowithurlstring:url];
  7. Dispatch_async (Dispatch_get_main_queue (), ^{
  8. UIImage *image = [UIImage imagewithdata:imagedata];
  9. Self.imageView.image = image;
  10. Self.imageView.frame = CGRectMake (0, 0, image.size.width, image.size.height);
  11. Self.scrollView.contentSize = image.size;
  12. }); });
  13. }

5. Third error, no release after queue creation, memory leak

View Plain

  1. -(void) Viewwillappear: (BOOL) animated
  2. {
  3. NSString *url = photo. URL;
  4. dispatch_queue_t downloadqueue = dispatch_queue_create ("Flickr downloader", NULL);
  5. Dispatch_async (Downloadqueue, ^{
  6. NSData *imagedata = [Flickrfetcher Imagedataforphotowithurlstring:url];
  7. Dispatch_async (Dispatch_get_main_queue (), ^{
  8. UIImage *image = [UIImage imagewithdata:imagedata];
  9. Self.imageView.image = image;
  10. Self.imageView.frame = CGRectMake (0, 0, image.size.width, image.size.height);
  11. Self.scrollView.contentSize = image.size;
  12. }); });
  13. dispatch_release (downloadqueue); Won ' t actually go away until queue is empty}

How iphone iOS uses Gcd,block

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.