Android UI operations are not thread-safe, and only the main thread can operate the UI. At the same time, the main thread has a certain time limit on UI operations (up to 5 seconds ). To perform some time-consuming operations (such as downloading and opening large files), Android provides some column mechanisms. The articles in the "android basics 02-thread security" series refer to a series of articles compiled by many online users and introduce the main methods. They are as follows:
Android basics 02 -- thread security 1: Definitions and Examples
Android basics 02 -- thread security 2: handler, message, and runnable
Android basics 02 -- thread security 3: Message, messagequeue, handler, Logoff
Android basics 02 -- thread security 4: handlerthread
Android basics 02 -- thread security 5: asynctask
In the above timer example, we mentioned the thread security issue. Next we will introduce it in detail.
I. Thread Security
First, let's take a look at the definition of thread security:
Thread security: if multiple threads in the process where your code is located run simultaneously, these threads may run the code at the same time. If the result of each running is the same as that of a single thread, and the value of other variables is the same as expected, it is thread-safe, or: an interface provided by a class or program is an atomic operation for a thread or a switch between multiple threads does not result in ambiguity in the execution result of this interface, that is to say, we do not need to consider synchronization issues.
When a program is started for the first time, Android starts a Linux Process and a main thread. By default, all components of the program will run in the process and thread. The main thread is mainly responsible for processing UI-related events, such as user button events, user touch screen events, and screen plotting events, and distribute related events to corresponding components for processing. Therefore, the main thread is often called the UI thread. The UI thread can interact with the components in the android UI toolkit. The single-thread model principle must be observed when developing Android applications:
Android UI operations are not thread-safe and must be executed in the UI thread.
When the main thread is performing some time-consuming operations, such as downloading a large image from the network or accessing the database, because the main thread is blocked by these time-consuming operations, it is impossible to respond to user events in a timely manner. From the user's perspective, the program will feel dead. If the program does not respond for a long time, the user may have to restart the system. To avoid this situation, Android sets a 5-second timeout time. Once the user's event fails to respond for more than 5 seconds due to the main thread blocking, android will pop up a dialog box with no response from the application.
Ii. Example
The following is a case study:
This program will design and implement the function of viewing the weather conditions of the specified city on the day,
1. First, you need to select a weather query service interface. Currently, there are many available interfaces, such as Yahoo's weather API and Google's weather API. This article selects Google's weather query API. This interface provides multiple query methods, which can be queried by specifying the longitude and latitude of a specific city or by city name.
2. enter the name of the city to be queried in the input box, and then click search.
3. after you click the query button, use the httpclient API that has been built in Android SDK to call Google's weather query API, and then parse the weather information of the specified City returned, and display the weather information on the title.
The main code is as follows:
Public class weatherreport extends activity implements onclicklistener {Private Static final string google_api_url = "http://www.google.com/ig/api? Weather = "; Private Static final string network_error =" network exception "; private edittext; @ override public void oncreate (bundle savedinstancestate) {super. oncreate (savedinstancestate); setcontentview (R. layout. main); edittext = (edittext) findviewbyid (R. id. weather_city_edit); button = (button) findviewbyid (R. id. goquery); button. setonclicklistener (this );}
@ Override public void onclick (view v) {// obtain the user-input city name string city = edittext. gettext (). tostring (); // call the Google weather API to query the weather condition of the specified city on the day string weather = getwetherbycity (city); // display the weather information on the title settitle (weather );}
public String getWetherByCity(String city) { HttpClient httpClient = new DefaultHttpClient(); HttpContext localContext = new BasicHttpContext(); HttpGet httpGet = new HttpGet(GOOGLE_API_URL + city); try { HttpResponse response = httpClient.execute(httpGet, localContext); if (response.getStatusLine().getStatusCode() != HttpStatus.SC_OK) { httpGet.abort(); } else { HttpEntity httpEntity = response.getEntity(); return parseWeather(httpEntity.getContent()); } } catch (Exception e) { Log.e("WeatherReport", "Failed to get weather", e); } finally { httpClient.getConnectionManager().shutdown(); } return NETWORK_ERROR; }}
After you enter the city name and click the button to query the city, the program calls the Google API interface to obtain the weather conditions of the specified city on the current day. To access the network, network access is time-consuming when the network is abnormal or the service is busy. To demonstrate timeout, you only need to create a network exception. The simplest way is to disconnect the network, start the program, and trigger a user event at the same time, for example, if you press the menu key and the main thread is blocked for a long time due to a network exception, the user's key event cannot be responded within five seconds, android will prompt an exception in which a program cannot respond.
3. subthread
The android UI is single-threaded. To avoid dragging the GUI, some time-consuming objects should be handed over to independent threads for execution. However, Android sends an error message calledfromwrongthreadexception when the background thread executes the UI object.
As in the previous example, it is wrong that the main thread is responsible for this operation. Therefore, we need to create a new sub-thread in the onclick method to call Google API to obtain weather data. The easiest way to think of Android Developers is as follows:
Public void onclick (view v) {// create a subthread to obtain weather information from the network during time-consuming Operations new thread () {@ override public void run () {// obtain the city name string city = edittext. gettext (). tostring (); // call the Google weather API to query the weather conditions of the specified city on the day string weather = getwetherbycity (city ); // display the weather information on the title settitle (weather );}}. start ();}
You will find that android will prompt that the program is terminated due to an exception. Why do simple code on other platforms still encounter errors when running on Android? If you observe the log information printed in logcat, you will find such an error log:
Android. View. viewroot $ calledfromwrongthreadexception: only the original thread that created a view hierarchy can touch its views.
From the error message, it is not difficult to see that android blocks other sub-threads from updating the attempt created by the UI thread. In this example, the title that displays the weather information is actually a textview created by the UI thread. Therefore, an error occurs when you change the textview in a subthread. This display violates the single-thread model principle: Android UI operations are not thread-safe and must be executed in the UI thread.