如何在我的应用程序中解决解析器错误?

时间:2012-01-05 12:48:47

标签: java android saxparser

我成功解析了我的xml文件,但现在我得到了null值。所以我在编码中犯了什么错误我不知道。我想在屏幕上显示我的字符串值。现在我试图以文本视图格式显示该字符串值,但我得到空值......

我的xml文件:

<Mobiles>
<Mobile>
<Phone>Nokia 1108</Phone>
<Network>GSM 900/1800 MHz</Network>
<Size>106x46x20 mm</Size>
<Ringtones>mono</Ringtones>
<SMS>yes</SMS>
<MMS>no</MMS>
<Email>no</Email>
<InstantMessaging >no</InstantMessaging>
</Mobile>

<Mobile>
<Phone>Nokia 1109</Phone>
<Network>GSM 900/1800 MHz</Network>
<Size>106x46x20 mm</Size>
<Ringtones>mono</Ringtones>
<SMS>yes</SMS>
<MMS>no</MMS>
<Email>no</Email>
<InstantMessaging >no</InstantMessaging>
</Mobile>

<Mobile>
<Phone>Nokia 1110</Phone>
<Network>GSM 900/1800 MHz</Network>
<Size>106x46x20 mm</Size>
<Ringtones>mono</Ringtones>
<SMS>yes</SMS>
<MMS>no</MMS>
<Email>no</Email>
<InstantMessaging >no</InstantMessaging>
</Mobile>

<Mobile>
<Phone>Nokia 1111</Phone>
<Network>GSM 900/1800 MHz</Network>
<Size>106x46x20 mm</Size>
<Ringtones>mono</Ringtones>
<SMS>yes</SMS>
<MMS>no</MMS>
<Email>no</Email>
<InstantMessaging >no</InstantMessaging>
</Mobile>
</Mobiles>

输出: enter image description here

2 个答案:

答案 0 :(得分:1)

只是简单地看一下你的代码,我会说问题是in_Mobiles变量上的状态转换。从文档的开头到结尾,它始终是true

characters(char[], int, int)方法中,第一个条件分支将占用所有字符:

if (this.in_Mobiles) {
    myParsedExampleDataSet.setMobiles(new String(ch, start, length));

使用in_Mobile时会重复相同的行为,如果你修复了第一个,那将是下一个罪魁祸首。

修改: 好吧,总的来说你的解析器实现有点不稳定。尝试这样的事情:

首先,您的ParsedExampleDataSet有点偏。

将其转换为Mobile对象列表,如下所示:

public class ParsedExampleDataSet extends ArrayList<Mobile>{
}

接下来,创建一个名为Mobile的bean类,如下所示:

class Mobile {
    private String Phone;
    private String Network;
    private String Size;
    private String Ringtones;
    private boolean SMS;
    private boolean MMS;
    private boolean Email;
    private boolean InstantMessaging;
    public String getPhone() {
        return Phone;
    }
    public void setPhone(String phone) {
        Phone = phone;
    }
    public String getNetwork() {
        return Network;
    }
    public void setNetwork(String network) {
        Network = network;
    }
    public String getSize() {
        return Size;
    }
    public void setSize(String size) {
        Size = size;
    }
    public String getRingtones() {
        return Ringtones;
    }
    public void setRingtones(String ringtones) {
        Ringtones = ringtones;
    }
    public boolean isSMS() {
        return SMS;
    }
    public void setSMS(boolean sMS) {
        SMS = sMS;
    }
    public boolean isMMS() {
        return MMS;
    }
    public void setMMS(boolean mMS) {
        MMS = mMS;
    }
    public boolean isEmail() {
        return Email;
    }
    public void setEmail(boolean email) {
        Email = email;
    }
    public boolean isInstantMessaging() {
        return InstantMessaging;
    }
    public void setInstantMessaging(boolean instantMessaging) {
        InstantMessaging = instantMessaging;
    }
}

最后,需要重新设计DefaultHandler子类。这样的事情应该有效。

class ExampleHandler extends DefaultHandler {
    private ParsedExampleDataSet Mobiles;
    private Mobile CurrentMobile;
    private StringBuilder Characters;
    public ParsedExampleDataSet getParsedExampleDataSet() {
        return Mobiles;
    }
    public void startDocument() throws SAXException {
        Mobiles = new ParsedExampleDataSet();
    }
    public void startElement(String namespaceUri, String localName, String qName, Attributes atts)
            throws SAXException {
        String name = localName.equals("") ? qName : localName;
        if ("Mobile".equals(name)) {
            CurrentMobile = new Mobile();
        }
        // Empty accumulated characters
        Characters = null;
    }
    public void characters(char[] ch, int offset, int length) throws SAXException {
        if (Characters == null) {
            Characters = new StringBuilder(length);
        }
        Characters.append(ch, offset, length);
    }
    public void endElement(String namespaceUri, String localName, String qName) throws SAXException {
        String name = localName.equals("") ? qName : localName;
        if ("Mobile".equals(name)) {
            Mobiles.add(CurrentMobile);
            CurrentMobile = null;
        } else if (CurrentMobile != null && Characters != null){
            String value = Characters.toString();
            if ("Phone".equals(name)) {
                CurrentMobile.setPhone(value);
            } else if ("Network".equals(name)) {
                CurrentMobile.setNetwork(value);
            } else if ("Size".equals(name)) {
                CurrentMobile.setSize(value);
            } else if ("Ringtones".equals(name)) {
                CurrentMobile.setRingtones(value);
            } else {
                boolean yes = "yes".equalsIgnoreCase(value.trim());
                if ("SMS".equals(name)) {
                    CurrentMobile.setSMS(yes);
                } else if ("MMS".equals(name)) {
                    CurrentMobile.setMMS(yes);
                } else if ("Email".equals(name)) {
                    CurrentMobile.setEmail(yes);
                } else if ("InstantMessaging".equals(name)) {
                    CurrentMobile.setInstantMessaging(yes);
                }
            }
        }
    }
}

而且,像这样运行它会产生一个结果:

SAXParser parser = SAXParserFactory.newInstance().newSAXParser();
ExampleHandler handler = new ExampleHandler();
InputSource is = new InputSource(/* your XML goes here as an inputstream or reader*/);
parser.parse(is, handler);
ParsedExampleDataSet mobiles = handler.getParsedExampleDataSet();
for (Mobile mobile : mobiles) {
    System.out.println(mobile.getPhone());
}

答案 1 :(得分:0)

为什么你在endElement方法中有真的?

 if (localName.equals("Mobiles")) {
                this.in_Mobiles = true;

这可能导致始终覆盖移动设备而不设置正确的字段。