我想开发一个应用程序,允许我从Android应用程序的形式上传数据作为服务器中的文本文件 这是主要活动类
package com.example.incrediblemachine.sendtest;
import android.app.Activity;
import android.os.AsyncTask;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;
import org.apache.http.NameValuePair;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.HttpClient;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.message.BasicNameValuePair;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
public class MainActivity extends Activity {
EditText msgTextField;
Button sendButton;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//make message text field object
msgTextField = (EditText) findViewById(R.id.msgTextField);
//make button object
sendButton = (Button) findViewById(R.id.sendButton);
}
public void send(View v)
{
//get message from message box
String msg = msgTextField.getText().toString();
//check whether the msg empty or not
if(msg.length()>0) {
HttpClient httpclient = new DefaultHttpClient();
HttpPost httppost = new HttpPost("http://ramsproject.16mb.com/sendorder.php");
try {
List<NameValuePair> nameValuePairs = new ArrayList<NameValuePair>(2);
nameValuePairs.add(new BasicNameValuePair("id", "01"));
nameValuePairs.add(new BasicNameValuePair("message", msg));
httppost.setEntity(new UrlEncodedFormEntity(nameValuePairs));
httpclient.execute(httppost);
msgTextField.setText(""); //reset the message text field
Toast.makeText(getBaseContext(),"Sent",Toast.LENGTH_SHORT).show();
}catch (IllegalStateException e)
{
e.printStackTrace();
}
catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
} else {
//display message if text field is empty
Toast.makeText(getBaseContext(),"All fields are required",Toast.LENGTH_SHORT).show();
}
}
}
第53行出现了例外情况 httpclient.execute(httppost);
异常说android.app.NetworkOnMainThreadException 我该如何解决这个问题
答案 0 :(得分:2)
只需使用一个帖子。
Thread thread = new Thread(new Runnable(){
@Override
public void run() {
try {
//Your code goes here
} catch (Exception e) {
e.printStackTrace();
}
}
});
thread.start();
在这个帖子中调用httpClient。
答案 1 :(得分:2)
您无法在MainThread中进行网络通话。您应该使用asynctask进行网络操作。您可以从以下链接中找到有关它的更多信息:
https://developer.android.com/reference/android/os/AsyncTask.html
另外,我建议您使用网络库来处理网络操作。您可以通过以下链接找到适合您的网络运营的好库:
答案 2 :(得分:0)
当应用程序尝试在其主线程上执行网络操作时引发此异常。 针对Honeycomb SDK或更高版本的应用程序可以在其主要事件循环线程上进行联网,以避免与网络相关的无响应情境的迟缓。你可以接受Documentation。
要解决此问题,您可以选择以下选项: 1.使用AsyncTasks 2.线程 3.处理程序
答案 3 :(得分:0)
我想在这里为您提供解决方案。为此,我想在您了解解决方案之前指出几点。
所有Android组件(Activity,Service,BroadcastReceiver,Fragment以及可视化显示数据的任何内容)都在UI线程或主线程中运行,以进一步理解此读取。
每个Android应用程序都在自己的进程上运行,并拥有唯一的用户ID。安装Android应用程序时,会给它一个唯一的用户ID。每当应用程序运行时,都会为程序执行提供单独的内存空间和路径。这个过程由它自己的内存Heap组成。该过程就像一个单独的环境,为您的应用程序提供运行代码或流程代码。
另一方面,线程是子流程或轻量级流程。它是在这个过程中产生的。当创建一个线程时,它会被赋予内存的一部分(堆栈)。一个进程可以产生许多线程。
一个线程无法访问另一个线程内存(堆栈),它对特定线程是私有的。但是他们可以访问进程内存(堆内存)。将堆内存视为全局内存。
每当为您的应用程序创建一个进程时,就会创建一个必需的线程。该线程称为主线程。在android中它也可能被称为UI线程。因为此线程处理您看到的所有UI组件(如活动,片段和服务(即使服务在后台运行,它在UI线程上运行)等。)
Android框架的创建方式使得他们希望处理主线程上的所有UI操作,从而为处理UI组件提供高优先级。因为UI是向用户显示的UI,并且如果在不处理UI的情况下冻结应用程序,则用户将不喜欢该应用程序。
这就是您获得“NetworkOnMainThread”异常的原因。因为Android限制运行长时间运行的操作,如网络访问,文件访问,数据库访问以及在UI线程上运行的那些处理。因为处理限制UI的响应需要花费很多时间,因为它没有为UI组件提供处理的机会。
我希望你明白为什么你现在得到这样的例外。长时间运行的操作不应限制UI线程操作。所以它应该从UI线程移动到另一个新线程(移动代码,你创建一个HttpClient,直到你收到它的响应)。 Android还为此提供了另一种选择。您可以创建一个AsyncTask,它为您处理线程创建过程。您可以只编写代码并将结果传递给UI线程。了解更多信息。
注意:所有线程都访问进程内存。但是,除非具有相同的USER ID,否则进程无法访问其他进程的内存。除非是来自您的一个申请,否则意味着。这可以使用AIDL接口完成。
我希望这个解决方案可以帮助您理解您获得的异常并解决它们。