类型不匹配:无法从 StringBuilder 转换为 String。

27

该方法返回给定URL的源代码。

private static String getUrlSource(String url) {
    try {
        URL localUrl = null;
        localUrl = new URL(url);
        URLConnection conn = localUrl.openConnection();
        BufferedReader reader = new BufferedReader(
            new InputStreamReader(conn.getInputStream()));
        String line = "";
        String html;
        StringBuilder ma = new StringBuilder();
        while ((line = reader.readLine()) != null) {
            ma.append(line);
        }
        return ma;
    } catch (Exception e) {
        Log.e("ERR",e.getMessage());
    }
}

它给了我这个错误:

Type mismatch: cannot convert from StringBuilder to String

还有两个选择:

  1. 将返回类型更改为StringBuilder。但我想让它返回一个字符串。
  2. 将ma的类型更改为String。更改后,字符串就没有append()方法了。

6
返回 ma 对象的字符串表示形式。 - Esailija
顺便提一下,你可能想要使用 ma.append(line).append(LINE_SEPERATOR),否则你的行会像 This is line 1.This is line 2.This is line 3. 一样混乱无序。 - corsiKa
3个回答

54

只需使用

return ma.toString();

替代

return ma;

ma.toString() 返回您的 StringBuilder 的字符串表示形式。

有关详细信息,请参见 StringBuilder#toString()

正如 Valeri Atamaniouk 在评论中建议的那样,您还应该在 catch 块中返回一些内容,否则您将会得到一个编译器错误:missing return statement,因此请进行编辑。

} catch (Exception e) {
    Log.e("ERR",e.getMessage());
}

为了

} catch (Exception e) {
    Log.e("ERR",e.getMessage());
    return null; //or maybe return another string
}

这是个不错的想法。


编辑

正如Esailija所建议的,这段代码中存在三种反模式。

} catch (Exception e) {           //You should catch the specific exception
    Log.e("ERR",e.getMessage());  //Don't log the exception, throw it and let the caller handle it
    return null;                  //Don't return null if it is unnecessary
}

所以我认为最好做这样的事情:
private static String getUrlSource(String url) throws MalformedURLException, IOException {
    URL localUrl = null;
    localUrl = new URL(url);
    URLConnection conn = localUrl.openConnection();
    BufferedReader reader = new BufferedReader(
            new InputStreamReader(conn.getInputStream()));
    String line = "";
    String html;
    StringBuilder ma = new StringBuilder();
    while ((line = reader.readLine()) != null) {
        ma.append(line);
    }
    return ma.toString();
}

然后,当你调用它时:

try {
    String urlSource = getUrlSource("http://www.google.com");
    //process your url source
} catch (MalformedURLException ex) {
    //your url is wrong, do some stuff here
} catch (IOException ex) {
    //I/O operations were interrupted, do some stuff here
}

请查看以下链接,了解有关Java反模式的详细信息:

函数在异常情况下也必须返回一个值。如果你还没有注意到的话。 - Valeri Atamaniouk
@ValeriAtamaniouk 是的,有时候会出现,但这超出了问题的范围。然而,这会是一个很好的评论,可以像我的建议一样添加行分隔符。 - corsiKa
2
吞噬异常、记录日志并返回null——同时出现了这三种反模式。令人印象深刻。 - Esailija

3

我在将StringBuilder转换为String时遇到了同样的问题,我使用了上面的代码,但是它并没有给出正确的解决方案。使用以上代码输出结果如下:

    String out=ma.toString();
// out=[Ljava.lang.String;@41e633e0

之后,我找到了正确的解决方案。思路是创建一个新的字符串实例,而不是像这样插入StringBuilder。

String out=new String(ma);

0

尝试

return ma.toString(); 因为您无法直接将stringbuilder变量存储到字符串变量中。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接