Хранить статические данные в Android - пользовательский ресурс? - PullRequest
19 голосов
/ 07 июля 2010

Я новичок в разработке под Android, и я немного поиграл с этим. Я пытался создать программу, имеющую небольшую коллекцию неизменяемых данных, похожую на базу данных. В C #, моем лучшем на данный момент языке, я бы использовал список пользовательских классов и сериализовал бы его в XML-файл, а затем считывал его в свое приложение во время выполнения. Я нашел папку ресурсов / xml в Android, но я не уверен, как мне поступить так, как я планирую. Каков наилучший способ сделать это?

Данные никогда не нужно будет менять. Пример:

Blob   | A  | B
----------------
Blob 1 | 23 | 42
Blob 2 | 34 | 21

Я знаю, что это похоже на таблицу, но использование базы данных для меня не имеет смысла, потому что данные никогда не изменятся, и мне понадобится способ сохранить их для первоначального заполнения базы данных в любом случае .

Так что в основном я ищу способ хранения несколько сложных статических данных в моем приложении. Есть идеи?

РЕДАКТИРОВАТЬ: я также увидел папку / raw. Так что я могу хранить вещи в / res / raw или / res / xml. Но я не уверен, что будет лучшим способом хранения / анализа данных ...

Ответы [ 4 ]

16 голосов
/ 08 июля 2010

Я думаю, что это ЛУЧШЕЕ решение, и я уже использую это для хранения статических данных в каждом моем проекте.

Для этого ... Вы можете сделать одну вещь, сделать один XML-файл, а именно:temp.xml "..и сохраните данные в temp.xml следующим образом:

  <?xml version="1.0" encoding="utf-8"?> 
<rootelement1>

    <subelement> Blob 1  
     <subsubelement> 23 </subsubelement>
     <subsubelement> 42 </subsubelement> 
    </subelement>

    <subelement>Blob 2      
    <subsubelement> 34 </subsubelement>
    <subsubelement> 21 </subsubelement>
    </subelement>


    </rootelement1>

и затем используйте метод XML PullParser для анализа данных.Вы можете иметь примеры кодирования техники PullParsing на Пример , обратитесь к этому примеру для лучшей идеи.

Наслаждайтесь !!

15 голосов
/ 07 июля 2010

Лучшим способом является использование иерархии ресурсов Android .

В каталоге res / values ​​/ вы можете хранить любое количество пар ключ-значение для нескольких основных типов данных. В вашем приложении вы можете ссылаться на них, используя автоматически сгенерированный идентификатор ресурса (имя, основанное на ключе вашего ресурса). См. Ссылку выше для получения дополнительной документации и деталей.

Android также поддерживает необработанные файлы данных. Вы можете хранить свои данные в каталоге файлов в каталоге res / raw / yourfile.dat

Вы создаете свои данные в любом текстовом формате, который хотите, а затем читаете их при запуске активности, используя apis доступа к ресурсам.

4 голосов
/ 18 сентября 2012

В прошлом я использовал Simple для разбора xml. Я думаю, что он имеет наименьшее количество кода, если вы знаете, что ожидать в XML, что в вашем случае вы делаете.

http://simple.sourceforge.net/

3 голосов
/ 23 февраля 2017

Согласно документ , /xml это путь.

Предоставление ресурсов

xml/ Произвольные файлы XML, которые можно прочитать во время выполнения, вызвав

Resources.getXML().

Здесь должны быть сохранены различные файлы конфигурации XML, например, конфигурация с возможностью поиска.

Документация для getXML()

Я также сделал рабочий пример:

  • структура XML:

    <?xml version="1.0" encoding="utf-8"?>
    <quizquestions>
        <quizquestion>
            <header_image_src>ic_help_black_24dp</header_image_src>
            <question>What is the Capital of U.S.A.?</question>
            <input_type>Radio</input_type>
            <answer correct="false">New York City</answer>
            <answer correct="true">Washington D.C.</answer>
            <answer correct="false">Chicago</answer>
            <answer correct="false">Philadelphia</answer>
        </quizquestion>
    
        <quizquestion>
            <header_image_src>ic_help_black_24dp</header_image_src>
            <question>What is the family name of the famous dutch painter Vincent Willem van .... ?</question>
            <input_type>EditText</input_type>              
            <answer correct="true">Gogh</answer>
        </quizquestion>
    </quizquestions>
    
  • класс Java для хранения проанализированных данных:

    public class QuizQuestion {
        private int headerImageResId;
        private String question;
        private String inputType;
        private ArrayList<String> answers;
        private ArrayList<Boolean> answerIsCorrect;
        private ArrayList<Integer> correctAnswerIndexes;
    
        /**
         * constructor for QuizQuestion object
         */
        QuizQuestion() {
            headerImageResId = 0;
            question = null;
            inputType = null;
            answers = new ArrayList<>();
            answerIsCorrect = new ArrayList<>();
            correctAnswerIndexes = new ArrayList<>();
        }
    
    
        public void setHeaderImageResId(int headerImageResId) {
            this.headerImageResId = headerImageResId;
        }
    
        public int getHeaderImageResId() {
            return headerImageResId;
        }
    
    
        void setQuestion(String question) {
            this.question = question;
        }
    
        public String getQuestion() {
            return question;
        }
    
    
        void setInputType(String inputType) {
            this.inputType = inputType;
        }
    
        public String getInputType() {
            return inputType;
        }
    
        void addAnswer(String answer, boolean isCorrect)
        {
            if (isCorrect)
                correctAnswerIndexes.add(answers.size());
            answers.add(answer);
            answerIsCorrect.add(isCorrect);
        }
    
    
        public ArrayList<String> getAnswers() {
            return answers;
        }
    
        public String getAnswer(int index)
        {
            // check index to avoid out of bounds exception
            if (index < answers.size()) {
                return answers.get(index);
            }
            else
            {
                return null;
            }
        }
    
        public int size()
        {
            return answers.size();
        }
    
    }
    
  • сам парсер:

    /**
     * Created by bivanbi on 2017.02.23..
     *
     * class to parse xml resource containing quiz data into ArrayList of QuizQuestion objects
     *
     */
    
    public class QuizXmlParser {
    
        public static String lastErrorMessage = "";
    
        /**
         * static method to parse XML data into ArrayList of QuizQuestion objects
         * @param activity is the calling activity
         * @param xmlResourceId is the resource id of XML resource to be parsed
         * @return null if parse error is occurred or ArrayList of objects if successful
         * @throws XmlPullParserException
         * @throws IOException
         */
        public static ArrayList<QuizQuestion> parse(Activity activity, int xmlResourceId)
                throws XmlPullParserException, IOException
        {
            String logTag = QuizXmlParser.class.getSimpleName();
            Resources res = activity.getResources();
            XmlResourceParser quizDataXmlParser = res.getXml(R.xml.quiz_data);
    
            ArrayList<String> xmlTagStack = new ArrayList<>();
            ArrayList<QuizQuestion> quizQuestions = new ArrayList<>();
    
            QuizQuestion currentQuestion = null;
    
            boolean isCurrentAnswerCorrect = false;
    
            quizDataXmlParser.next();
            int eventType = quizDataXmlParser.getEventType();
            while (eventType != XmlPullParser.END_DOCUMENT)
            {
                //  begin document
                if(eventType == XmlPullParser.START_DOCUMENT)
                {
                    Log.d(logTag,"Begin Document");
                }
                //  begin tag
                else if(eventType == XmlPullParser.START_TAG)
                {
                    String tagName = quizDataXmlParser.getName();
                    xmlTagStack.add(tagName);
                    Log.d(logTag,"Begin Tag "+tagName+", depth: "+xmlTagStack.size());
                    Log.d(logTag,"Tag "+tagName+" has "+quizDataXmlParser.getAttributeCount()+" attribute(s)");
    
                    // this is a beginning of a quiz question tag so create a new QuizQuestion object
                    if (tagName.equals("quizquestion")){
                        currentQuestion = new QuizQuestion();
                    }
                    else if(tagName.equals("answer"))
                    {
                        isCurrentAnswerCorrect = quizDataXmlParser.getAttributeBooleanValue(null,"correct",false);
                        if (isCurrentAnswerCorrect == true) {
                            Log.d(logTag, "Tag " + tagName + " has attribute correct = true");
                        }
                        else
                        {
                            Log.d(logTag, "Tag " + tagName + " has attribute correct = false");
                        }
                    }
                }
                //  end tag
                else if(eventType == XmlPullParser.END_TAG)
                {
                    String tagName = quizDataXmlParser.getName();
                    if (xmlTagStack.size() < 1)
                    {
                        lastErrorMessage = "Error 101: encountered END_TAG "+quizDataXmlParser.getName()+" while TagStack is empty";
                        Log.e(logTag, lastErrorMessage);
                        return null;
                    }
                    xmlTagStack.remove(xmlTagStack.size()-1);
                    Log.d(logTag,"End Tag "+quizDataXmlParser.getName()+", depth: "+xmlTagStack.size());
    
                    //  reached the end of a quizquestion definition, add it to the array
                    if (tagName.equals("quizquestion")){
                        if (currentQuestion != null)
                            quizQuestions.add(currentQuestion);
                        currentQuestion = null;
                    }
                }
                //  text between tag begin and end
                else if(eventType == XmlPullParser.TEXT)
                {
                    String currentTag = xmlTagStack.get(xmlTagStack.size()-1);
                    String text = quizDataXmlParser.getText();
                    Log.d(logTag,"Text: "+text+", current tag: "+currentTag+", depth: "+xmlTagStack.size());
    
                    if (currentQuestion == null) {
                        Log.e(logTag,"currentQuestion is not initialized! text: "+text+", current tag: "+currentTag+", depth: "+xmlTagStack.size());
                        continue;
                    }
    
                    if (currentTag.equals("header_image_src"))
                    {
                        int drawableResourceId = activity.getResources().getIdentifier(text, "drawable", activity.getPackageName());
                        currentQuestion.setHeaderImageResId(drawableResourceId);
                    }
                    else if (currentTag.equals("question"))
                    {
                        currentQuestion.setQuestion(text);
                    }
                    else if (currentTag.equals("answer"))
                    {
                        currentQuestion.addAnswer(text, isCurrentAnswerCorrect);
                    }
                    else if (currentTag.equals("input_type"))
                    {
                        currentQuestion.setInputType(text);
                    }
                    else
                    {
                        Log.e(logTag,"Unexpected tag "+currentTag+" with text: "+text+", depth: "+xmlTagStack.size());
                    }
                }
                eventType = quizDataXmlParser.next();
            }
            Log.d(logTag,"End Document");
            return quizQuestions;
        }
    
    }
    
  • и, наконец, вызов парсера:

    //  read quiz data from xml resource quiz_data
    try {
        quizQuestions = QuizXmlParser.parse(this,R.xml.quiz_data);
        Log.d("Main","QuizQuestions: "+quizQuestions);
    
    } catch (XmlPullParserException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
        quizQuestions = null;
    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
        quizQuestions = null;
    }
    
    if (quizQuestions == null)
    {
        Toast.makeText(this,"1001 Failed to parse Quiz XML, sorry", Toast.LENGTH_LONG).show();
        finish();
    }
    
...