在android中执行doInBackground()方法时出现致命异常?

时间:2014-06-05 14:12:33

标签: android

我试图从yahoo weather api中获取一些数据,但它在doBackGround()中显示了一个致命异常。第一次它会正常运行,但第二次运行,它显示我这个错误。我尝试使用此代码并在此方法中显示错误

  String url1 = src.substring(1, src.length() - 2);

使用代码是:

package com.gird.completeontologyproject;

import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.Reader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.StringTokenizer;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.protocol.BasicHttpContext;
import org.apache.http.protocol.HttpContext;
import org.w3c.dom.Document;
import org.w3c.dom.Node;
import org.xml.sax.SAXException;

import android.app.Activity;
import android.app.ProgressDialog;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.AsyncTask;
import android.os.Bundle;
import android.widget.ImageView;
import android.widget.TextView;
import android.widget.Toast;

public class WeatherSHow extends Activity {
    ImageView icon1 = null;
    TextView date = null, temp = null, condition = null, humidity = null,
            wind = null;
    ProgressDialog dialog;
    String temperature = null, date1 = null, condition1 = null,
            humidity1 = null, wind1 = null, link = null;
    ArrayList<String> weather=null;
    Bitmap icon = null;

    protected void onCreate(Bundle state) {
        super.onCreate(state);
        setContentView(R.layout.weather_pref);
        icon1 = (ImageView) findViewById(R.id.icon);
        date = (TextView) findViewById(R.id.dateText);
        temp = (TextView) findViewById(R.id.tempText);
        condition = (TextView) findViewById(R.id.conditionText);
        humidity = (TextView) findViewById(R.id.humidityText);
        wind = (TextView) findViewById(R.id.windText);

        new RetriveWeatherTask().execute();
    }

    class RetriveWeatherTask extends AsyncTask<Void, String, String> {

        protected void onPreExecute() {
            dialog = new ProgressDialog(WeatherSHow.this);
            dialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);
            dialog.setMessage("Loading...");
            dialog.setCancelable(false);
            dialog.show();
        }

        @Override
        protected String doInBackground(Void... params) {
            String Result = "";
            String uri = "http://weather.yahooapis.com/forecastrss?w=2295415&u=c;";
            HttpClient httpclient = new DefaultHttpClient();
            HttpContext localcontext = new BasicHttpContext();
            HttpGet httpget = new HttpGet(uri);
            try {
                HttpResponse httpresponse = httpclient.execute(httpget,
                        localcontext);
                HttpEntity entity = httpresponse.getEntity();
                if (entity != null) {
                    InputStream inputstream = entity.getContent();
                    Reader resder = new InputStreamReader(inputstream);
                    BufferedReader bufferReader = new BufferedReader(resder);
                    StringBuilder stringBuilder = new StringBuilder();
                    String ReadLine = null;
                    while ((ReadLine = bufferReader.readLine()) != null) {
                        stringBuilder.append(ReadLine + "\n");
                    }

                    Result = stringBuilder.toString();
                }
            } catch (ClientProtocolException e) {
                Toast.makeText(getApplicationContext(), e.toString(),
                        Toast.LENGTH_LONG).show();
            } catch (IOException e) {
                Toast.makeText(getApplicationContext(), e.toString(),
                        Toast.LENGTH_LONG).show();
            }

            Document docu = null;
            DocumentBuilder parse1 = null;
            DocumentBuilderFactory docuFactory = DocumentBuilderFactory
                    .newInstance();
            try {
                parse1 = docuFactory.newDocumentBuilder();
                docu = parse1
                        .parse(new ByteArrayInputStream(Result.getBytes()));
            } catch (ParserConfigurationException ed) {
                Toast.makeText(getApplicationContext(), ed.toString(),
                        Toast.LENGTH_LONG).show();
            } catch (SAXException e) {
                Toast.makeText(getApplicationContext(), e.toString(),
                        Toast.LENGTH_LONG).show();
            } catch (IOException e) {
                Toast.makeText(getApplicationContext(), e.toString(),
                        Toast.LENGTH_LONG).show();
            }

            Node tempretureNode = docu.getElementsByTagName(
                    "yweather:condition").item(0);
            temperature = tempretureNode.getAttributes().getNamedItem("temp")
                    .getNodeValue().toString();

            Node TempratureUnit = docu.getElementsByTagName("yweather:units")
                    .item(0);
            temperature = temperature
                    + " "
                    + TempratureUnit.getAttributes()
                            .getNamedItem("temperature").getNodeValue()
                            .toString();

            Node dateNode = docu.getElementsByTagName("yweather:forecast")
                    .item(0);
            date1 = dateNode.getAttributes().getNamedItem("date")
                    .getNodeValue().toString();

            Node conditionNode = docu
                    .getElementsByTagName("yweather:condition").item(0);
            condition1 = conditionNode.getAttributes().getNamedItem("text")
                    .getNodeValue().toString();

            Node humidityNode = docu
                    .getElementsByTagName("yweather:atmosphere").item(0);
            humidity1 = humidityNode.getAttributes().getNamedItem("humidity")
                    .getNodeValue().toString();

            Node windNode = docu.getElementsByTagName("yweather:wind").item(0);
            wind1 = windNode.getAttributes().getNamedItem("speed")
                    .getNodeValue().toString();

            Node windUnits = docu.getElementsByTagName("yweather:units")
                    .item(0);
            wind1 = wind1
                    + " "
                    + windUnits.getAttributes().getNamedItem("speed")
                            .getNodeValue().toString();

            String desc = docu.getElementsByTagName("item").item(0)
                    .getChildNodes().item(13).getTextContent().toString();
            StringTokenizer str = new StringTokenizer(desc, "<=>");
            String src = str.nextToken();
//Exception In this Method.
            String url1 = src.substring(1, src.length() - 2);
            Pattern TAG_REGEX = Pattern.compile("(.+?)<br />");
            Matcher matcher = TAG_REGEX.matcher(desc);
            weather=new ArrayList<String>();
            while (matcher.find()) {
                weather.add(matcher.group(1));
            }

            Pattern links = Pattern.compile("(.+?)<BR/>");
            matcher = links.matcher(desc);
            while (matcher.find()) {
                link = matcher.group(1);
            }

            InputStream in = null;
            try {
                // in = OpenHttpConnection(url1);
                int response = -1;
                URL url = new URL(url1);
                URLConnection conn = url.openConnection();

                if (!(conn instanceof HttpURLConnection))
                    throw new IOException("Not an HTTP connection");
                HttpURLConnection httpConn = (HttpURLConnection) conn;
                httpConn.setAllowUserInteraction(false);
                httpConn.setInstanceFollowRedirects(true);
                httpConn.setRequestMethod("GET");
                httpConn.connect();
                response = httpConn.getResponseCode();
                if (response == HttpURLConnection.HTTP_OK) {
                    in = httpConn.getInputStream();
                }
                icon = BitmapFactory.decodeStream(in);
                in.close();
            } catch (IOException e1) {
                e1.printStackTrace();
            }
            return Result;
        }

        protected void onPostExecute(String result) {
            System.out.println("POST EXECUTE");
            if (dialog.isShowing())
                dialog.dismiss();
            temp.setText("Temperature: " + temperature);
            condition.setText("Condition: " + condition1);
            date.setText("Date: " + date1);
            humidity.setText("Humidity: " + humidity1);
            wind.setText("Wind: " + wind1);
            icon1.setImageBitmap(icon);
        }
    }

}

我如何解决此错误: 错误日志:

06-05 19:32:11.876: E/Trace(4418): error opening trace file: No such file or directory (2)
06-05 19:32:17.584: E/AndroidRuntime(4418): FATAL EXCEPTION: AsyncTask #1
06-05 19:32:17.584: E/AndroidRuntime(4418): java.lang.RuntimeException: An error occured while executing doInBackground()
06-05 19:32:17.584: E/AndroidRuntime(4418):     at android.os.AsyncTask$3.done(AsyncTask.java:299)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at java.util.concurrent.FutureTask$Sync.innerSetException(FutureTask.java:273)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at java.util.concurrent.FutureTask.setException(FutureTask.java:124)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:307)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at java.util.concurrent.FutureTask.run(FutureTask.java:137)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:230)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1076)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:569)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at java.lang.Thread.run(Thread.java:856)
06-05 19:32:17.584: E/AndroidRuntime(4418): Caused by: java.lang.StringIndexOutOfBoundsException: length=1; regionStart=1; regionLength=-2
06-05 19:32:17.584: E/AndroidRuntime(4418):     at java.lang.String.startEndAndLength(String.java:593)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at java.lang.String.substring(String.java:1474)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at com.gird.completeontologyproject.WeatherSHow$RetriveWeatherTask.doInBackground(WeatherSHow.java:169)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at com.gird.completeontologyproject.WeatherSHow$RetriveWeatherTask.doInBackground(WeatherSHow.java:1)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at android.os.AsyncTask$2.call(AsyncTask.java:287)
06-05 19:32:17.584: E/AndroidRuntime(4418):     at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305)

4 个答案:

答案 0 :(得分:0)

您的src.length()返回1。 在致电String.substring()

之前检查一下

答案 1 :(得分:0)

src的长度是多少?它太短了,这就是错误的原因。

您应该检查该行之前的长度,如下所示:

String url1 = "";
if(src.lenth() > 4)
    url1 = src.substring(1, src.length() - 2);
else
    return "";

4是因为你从第二个字符(索引1)开始,并在src长度之前的第二个字符串完成(最小4-2 = 2)。你可以把其他if语句,如果你知道子串应该是什么样子以及应该多长时间。

你不需要其他,因为url1已经设置为“”但你可以根据你的代码放一些Toast或其他东西。

答案 2 :(得分:0)

你在WeatherSHow.java:169得到 StringIndexOutOfBoundsException ..所以@Zoran建议请检查长度

String url1 = "";
if(src.lenth() > 4)
    url1 = src.substring(1, src.length() - 2);

,您正试图在Toast中显示太多doInBackground()条消息,这些消息正在创建问题。您无法更新doInBackground()中的用户界面..在你的onPostExecute()..

您可以将Toast打包在runOnUIThread()中,但这不是最佳解决方案。 发生错误时应在catch块中设置一个布尔标志,然后在ToastonProgressUpdate()或任何其他具有UI访问权限的方法中显示适当的onPostExecute()。真。

选中此link以了解有关异步任务的更多信息..

答案 3 :(得分:0)

这是你的代码:

String url1 = src.substring(1, src.length() - 2);

此代码存在以下问题:Caused by: java.lang.StringIndexOutOfBoundsException: length=1; regionStart=1; regionLength=-2src只有1个字符,因此当您致电src.length() - 2时返回-1。

我的解决方案是,您必须在调用String方法之前检查substring的长度。

类似的东西:

int length = src.length();
int start = 1;
int end = length - 2;
String  url1 = "";
if(length > start && length < end){
    url1 = src.substring(1, src.length() - 2);
}

希望有所帮助!