17

Tôi mới phát triển Android và tôi đã từng chơi với nó một chút. Tôi đã cố tạo một chương trình có bộ sưu tập dữ liệu không thay đổi nhỏ như cơ sở dữ liệu. Trong C#, ngôn ngữ tốt nhất hiện tại của tôi, tôi muốn sử dụng một List của một lớp tùy chỉnh và tuần tự hóa cho một tệp xml, sau đó đọc nó vào ứng dụng của tôi khi chạy. Tôi tìm thấy thư mục tài nguyên/xml trong Android, nhưng tôi không chắc chắn làm thế nào tôi sẽ đi về làm những gì tôi đang hình dung. Điều gì sẽ là cách tốt nhất để thực hiện việc này?Lưu trữ dữ liệu tĩnh trong Android - tài nguyên tùy chỉnh?

Dữ liệu sẽ không bao giờ cần phải thay đổi. Ví dụ:

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

tôi từng biết đã đặt ra như một bảng, nhưng sử dụng một cơ sở dữ liệu không thực sự có ý nghĩa với tôi bởi vì các dữ liệu sẽ không bao giờ thay đổi, và tôi sẽ cần một cách để lưu trữ ban đầu cư cơ sở dữ liệu anyway.

Vì vậy, về cơ bản tôi đang tìm cách lưu trữ dữ liệu tĩnh phức tạp trong ứng dụng của mình. Bất kỳ ý tưởng?

EDIT: Tôi cũng thấy thư mục/raw. Vì vậy, tôi có thể lưu trữ mọi thứ trong/res/raw hoặc/res/xml. Nhưng tôi không chắc chắn cách nào là cách tốt nhất để lưu trữ/phân tích dữ liệu ...

Trả lời

13

Cách tốt nhất là sử dụng Android Resource Heirarchy.

Trong thư mục res/values ​​/, bạn có thể lưu trữ bất kỳ số lượng cặp khóa-giá trị nào cho một số loại dữ liệu cơ bản. Trong ứng dụng của bạn, bạn sẽ đề cập đến chúng bằng cách sử dụng một id tài nguyên tự tạo (tên dựa trên khóa tài nguyên của bạn). Xem liên kết ở trên để biết thêm tài liệu và chi tiết.

Android cũng hỗ trợ các tệp dữ liệu thô. Bạn có thể lưu trữ dữ liệu của mình trong thư mục tệp dưới dạng res/raw/yourfile.dat

Bạn tạo dữ liệu theo bất kỳ định dạng văn bản nào bạn muốn và sau đó đọc nó khi khởi động hoạt động bằng cách sử dụng apis truy cập tài nguyên.

+0

rằng sẽ tốt hơn hoặc tồi tệ hơn lưu trữ nó trong một hình thức xml và đọc nó trong? và nếu tôi đã sử dụng biểu mẫu xml, tôi sẽ đọc nó bằng cách nào? – NickAldwin

+1

@NickAldwin Tốt hơn ở chỗ bạn có thể lưu trữ ở bất kỳ định dạng nào bạn muốn, tệ hơn trong bạn không có sẵn các API để phân tích cú pháp dữ liệu. Bạn cũng có thể sử dụng phân cấp tài nguyên sẽ tốt hơn. Tôi sẽ sửa bài viết của tôi với các chi tiết. – CodeFusionMobile

+1

Điều tôi lo lắng với res/values ​​/ là tôi không có kế hoạch lưu trữ dữ liệu trong các cặp một-một (như trong ví dụ trên). Vì vậy, có được xây dựng trong apis để phân tích cú pháp xml tập tin khác với những người trong hệ thống phân cấp được chỉ định trong liên kết bạn đăng? EDIT: TypedArray sẽ làm việc cho một lớp tùy chỉnh (như ví dụ "Blob" ở trên)? Đó có phải là con đường để đi? – NickAldwin

16

Tôi nghĩ đây là giải pháp TỐT NHẤT và tôi đã sử dụng giải pháp này để lưu trữ dữ liệu tĩnh trong mỗi dự án của mình.

Cho rằng ... Bạn có thể làm một việc, làm cho một tập tin xml cụ thể là "temp.xml" ..và lưu trữ dữ liệu trong temp.xml như sau:

<?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> 

và sau đó sử dụng XML PullParser kỹ thuật phân tích cú pháp dữ liệu. Bạn có thể có mẫu mã hóa kỹ thuật PullParsing trên Example, tham khảo ví dụ này để có ý tưởng tốt hơn.

Tận hưởng !!

+0

Vâng, đó là kỹ thuật tôi đã kết thúc, như đã thảo luận về các nhận xét của câu trả lời được chấp nhận. Tôi thực sự tìm thấy các hướng dẫn ở đây là tốt nhất cho XmlPullParser: http://www.ibm.com/developerworks/opensource/library/x-android/index.html – NickAldwin

+0

Tôi nghĩ rằng tôi đã upvoted bạn ... oops! – NickAldwin

+0

không thể cập nhật giá trị trường xml giống như này để thay đổi khi người đó sửa đổi nó.Đối với Blob 1 thành sumit Sharma

4

Tôi đã sử dụng tính năng Phân tích cú pháp xml đơn giản trong quá khứ. Tôi nghĩ rằng nó có số tiền ít nhất của mã nếu bạn biết những gì mong đợi trong xml, mà trong trường hợp của bạn bạn làm.

http://simple.sourceforge.net/

1

Theo doc, /xml là con đường để đi.

Providing Resources

xml/ file XML Arbitrary có thể được đọc tại thời gian chạy bằng cách gọi

Resources.getXML(). 

file cấu hình XML khác nhau phải được lưu ở đây, chẳng hạn như một cấu hình tìm kiếm.

Documentation for getXML()

Tôi cũng làm một ví dụ làm việc:

  • cấu trúc 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> 
    
  • lớp Java để chứa dữ liệu phân tích cú pháp:

    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(); 
        } 
    
    } 
    
  • phân tích cú pháp riêng của mình:

    /** 
    * 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; 
        } 
    
    } 
    
  • và cuối cùng, gọi phân tích cú pháp:

    // 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(); 
    }