java攻城獅之路(Android篇)--SQLite

一.Junit
    1.怎麼使用
        在AndroidManifest.xml文件中進行配置, 在manifest借點下配置instrumentation, 在application借點下配置uses-library
        定義類繼承AndroidTestCast
        定義測試方法, Run As JunitTest
        若是須要判斷測試結果, 可使用Assert.assertEquals()方法.java

下面是利用獨立的測試工程JunitTest來測試工程Junit:android

package com.shellway.junit;

public class Service {
      public int divide(int a,int b){
          return a/b;
      }
}
Service.java
package com.shellway.junit;

import junit.framework.Assert;
import android.test.AndroidTestCase;

public class TestT extends AndroidTestCase {
    public void test1(){
        Service service = new Service();
        System.out.println(service.divide(10, 2));
    }
    public void test2(){
        Service service = new Service();
        System.out.println(service.divide(10, 0));
    }
    public void test3(){
        Service service = new Service();
        Assert.assertEquals(2.5, service.divide(10, 4));
    }
}
TestT.java
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.shellway.junit"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
        android:minSdkVersion="16"
        android:targetSdkVersion="21" />
       <instrumentation
        android:targetPackage="com.shellway.junit"
        android:name="android.test.InstrumentationTestRunner" />
    
    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
        <uses-library android:name="android.test.runner" />
        <activity
            android:name=".MainActivity"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>
</manifest>
AndroidManifest.xml

JunitTest工程中的:sql

package com.shellway.junit.test;

import junit.framework.Assert;

import com.shellway.junit.Service;

import android.test.AndroidTestCase;

public class MyTest extends AndroidTestCase {
    public void test1(){
        Service service = new Service();
        System.out.println(service.divide(10,2));
    }
    public void test2(){
        Service service = new Service();
        System.out.println(service.divide(10, 0));
    }
    public void test3(){
        Service service = new Service();
        Assert.assertEquals(2.5, service.divide(10, 4));
    }
}
MyTest.java
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.shellway.junit.test"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk android:minSdkVersion="16" />

    <instrumentation
        android:name="android.test.InstrumentationTestRunner"
        android:targetPackage="com.shellway.junit" />

    <application
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name" >
        <uses-library android:name="android.test.runner" />
    </application>
</manifest>
AndroidManifest.xml


二.日誌
    1.怎麼使用
        Log.v(), d(), i(), w(), e()
        能夠按級別輸出日子信息, 能夠指定Tagshell

package com.example.logcat;

import android.test.AndroidTestCase;
import android.util.Log;

public class LogTest extends AndroidTestCase {
    public void test1(){
        System.out.println("System.out");
        System.err.println("System.out");
    }
    public void test2(){
        Log.v("LogTest", "verbose");
        Log.d("LogTest", "debug");
        Log.i("LogTest", "info");
        Log.w("LogTest", "warning");
        Log.e("LogTest", "error");
    }
}
LogTest.java
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.example.logcat"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
        android:minSdkVersion="8"
        android:targetSdkVersion="21" />
        <instrumentation
        android:targetPackage="com.example.logcat"
        android:name="android.test.InstrumentationTestRunner" />
    
    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
     <uses-library android:name="android.test.runner" />
        <activity
            android:name=".MainActivity"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>
</manifest>
AndroidManifest.xml


三.讀寫文件
    1.讀寫SD卡
        獲取SD卡路徑要使用Environment.getExternalStorageDirectory()
        最好在使用SD卡以前判斷狀態, Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)
        寫入SD卡須要權限, android.permission.WRITE_EXTERNAL_STORAGE數據庫

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:paddingBottom="@dimen/activity_vertical_margin"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    tools:context="com.shellway.output.MainActivity" >

    <EditText
        android:id="@+id/nameET"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:hint="請輸入文件名" />

    <EditText
        android:id="@+id/contentET"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_below="@id/nameET"
        android:hint="請輸入文件內容"
        android:inputType="textMultiLine"
        android:minLines="3" />

    <Button
        android:id="@+id/sdcBT"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_below="@id/contentET"
        android:onClick="onClick"
        android:text="保存到SD卡" />

    <Button
        android:id="@+id/romBT"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_below="@id/contentET"
        android:layout_toRightOf="@id/sdcBT"
        android:onClick="onClick"
        android:text="保存到ROM" />

</RelativeLayout>
activity_main.xml
package com.shellway.fileoutput01;

import com.shellway.service.FileService;

import android.support.v7.app.ActionBarActivity;
import android.os.Bundle;
import android.os.Environment;
import android.view.View;
import android.widget.EditText;
import android.widget.Toast;

public class MainActivity extends ActionBarActivity {

    private EditText editText1;
    private EditText editText2;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    }

    public void onClick(View view) {
        try {
             editText1 = (EditText) findViewById(R.id.nameET);
             editText2 = (EditText) findViewById(R.id.contentET);
            String name = editText1.getText().toString();
            String content = editText2.getText().toString();
            
            FileService service = new FileService(this);
            switch (view.getId()) {
            case R.id.sdcBT:
                System.out.println("SD卡");
                //先判斷SD的狀態
                if (!(Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED))) {
                    Toast.makeText(getApplicationContext(), "SD卡狀態異常,不能保存", Toast.LENGTH_SHORT);
                    return;
                }
                service.saveToSDcard(name,content);
                break;
            case R.id.romBT:
                System.out.println("ROM");
                service.saveToROM(name,content);
                break;
            }
            Toast.makeText(getApplicationContext(), "保存成功", Toast.LENGTH_SHORT).show();
        } catch (Exception e) {
            e.printStackTrace();
            Toast.makeText(getApplicationContext(), "保存失敗", Toast.LENGTH_SHORT).show();
        }
    }
}
MainActivity.java
package com.shellway.service;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;

import android.content.Context;
import android.os.Environment;

public class FileService {
    private Context context;

    public FileService(Context context) {
        this.context = context;
    }

    //有異常先拋出,給主程序catch
    public void saveToSDcard(String name, String content) throws Exception {
        //獲取SD卡所在目錄,這種方式兼容全部版本
        File file = new File(Environment.getExternalStorageDirectory(),name);
        //建立輸出流,指向SD卡所在目錄
        FileOutputStream fileOutputStream = new FileOutputStream(file);
        //寫出文件內容,默認UTF-8
        fileOutputStream.write(content.getBytes());
        fileOutputStream.close();
        
        System.out.println("總空間:"+file.getTotalSpace()); 
        System.out.println("剩餘空間:"+file.getFreeSpace());
    }
    
    public void saveToROM(String name, String content) throws Exception {
        /**
         * openFileOutput()方法只有在MainActivity可用,如今通過傳它的構造函數過來,在這裏再調用它
         * 如今openFileOutput()方法的做用是:它會在當前環境(即當前應用在所在的文件夾下)根據name建立一個輸出流
         * 模式:MODE_PRIVATE。表示只有當前應用能訪問這個文件,其它應用訪問不了
         */
        FileOutputStream fos = context.openFileOutput(name, Context.MODE_APPEND);
        fos.write(content.getBytes());
        fos.close();
        //往手機上寫內容不用申請權限,寫入SD卡纔要。
    }
}
FileService.java

    2.讀寫手機
        可使用Context.openFileOutput(String, int)方法打開輸出流
        指定文件名後會自動在當前應用所在文件夾下生成files文件夾, 在其中建立文件
        int參數是文件權限, 能夠是使用Context下的常量進行設置,即:app

      第一個參數,表明文件名稱,注意這裏的文件名稱不能包括任何的/或者/這種分隔符,
      只能是文件名 該文件會被保存在/data/data/應用名稱/files/chenzheng_java.txt 。
      第二個參數,表明文件的操做模式 :
      MODE_PRIVATE 私有(只能建立它的應用訪問) 重複寫入時會文件覆蓋
      MODE_APPEND 私有 重複寫入時會在文件的末尾進行追加,而不是覆蓋掉原來的文件
      MODE_WORLD_READABLE 公用 可讀
      MODE_WORLD_WRITEABLE 公用 可讀寫dom

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    >
<TextView  
    android:layout_width="fill_parent" 
    android:layout_height="wrap_content" 
    android:text="請您輸入要保存的內容:"
    />
 <EditText
     android:id="@+id/addText"
     android:layout_width="fill_parent" 
    android:layout_height="wrap_content"
    android:hint="請您在此處輸入文件內容!"
 />   
 <Button 
     android:id="@+id/addButton"
     android:layout_width="wrap_content" 
    android:layout_height="wrap_content"
     android:text="save"
 />
 <Button
     android:id="@+id/showButton"
     android:layout_width="wrap_content" 
    android:layout_height="wrap_content"
    android:text="show"
 />
 <TextView
     android:id="@+id/showText"  
    android:layout_width="fill_parent" 
    android:layout_height="wrap_content" 
    />
 
</LinearLayout>
AndroidManifest.xml
package cn.com.file;

import java.io.ByteArrayOutputStream;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;

public class FileTest extends Activity {
    private EditText editText;
    private TextView showTextView;
    // 要保存的文件名
    private String fileName = "chenzheng_java.txt";

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        // 獲取頁面中的組件
        editText = (EditText) findViewById(R.id.addText);
        showTextView = (TextView) findViewById(R.id.showText);
        Button addButton = (Button) this.findViewById(R.id.addButton);
        Button showButton = (Button) this.findViewById(R.id.showButton);
        // 綁定單擊事件
        addButton.setOnClickListener(listener);
        showButton.setOnClickListener(listener);

    }

    // 聲明監聽器
    private View.OnClickListener listener = new OnClickListener() {
        public void onClick(View v) {
            Button view = (Button) v;
            switch (view.getId()) {
            case R.id.addButton:
                save();
                break;
            case R.id.showButton:
                read();
                break;

            }

        }

    };

    /**
     *@author chenzheng_Java 
     *保存用戶輸入的內容到文件
     */
    private void save() {

        String content = editText.getText().toString();
        try {
            /* 根據用戶提供的文件名,以及文件的應用模式,打開一個輸出流.文件不存系統會爲你建立一個的,
             * 至於爲何這個地方還有FileNotFoundException拋出,我也比較納悶。在Context中是這樣定義的
             *   public abstract FileOutputStream openFileOutput(String name, int mode)
             *   throws FileNotFoundException;
             * openFileOutput(String name, int mode);
             * 第一個參數,表明文件名稱,注意這裏的文件名稱不能包括任何的/或者/這種分隔符,只能是文件名
             *          該文件會被保存在/data/data/應用名稱/files/chenzheng_java.txt
             * 第二個參數,表明文件的操做模式
             *             MODE_PRIVATE 私有(只能建立它的應用訪問) 重複寫入時會文件覆蓋
             *             MODE_APPEND  私有   重複寫入時會在文件的末尾進行追加,而不是覆蓋掉原來的文件
             *             MODE_WORLD_READABLE 公用  可讀
             *             MODE_WORLD_WRITEABLE 公用 可讀寫
             *  */
            FileOutputStream outputStream = openFileOutput(fileName,
                    Activity.MODE_PRIVATE);
            outputStream.write(content.getBytes());
            outputStream.flush();
            outputStream.close();
            Toast.makeText(FileTest.this, "保存成功", Toast.LENGTH_LONG).show();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }

    }

    /**
     * @author chenzheng_java 
     * 讀取剛纔用戶保存的內容
     */
    private void read() {
        try {
            FileInputStream inputStream = this.openFileInput(fileName);
            byte[] bytes = new byte[1024];
            ByteArrayOutputStream arrayOutputStream = new ByteArrayOutputStream();
            while (inputStream.read(bytes) != -1) {
                arrayOutputStream.write(bytes, 0, bytes.length);
            }
            inputStream.close();
            arrayOutputStream.close();
            String content = new String(arrayOutputStream.toByteArray());
            showTextView.setText(content);

        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }

    }

}
FileTest.java

結果圖:編輯器

對於這個程序,重要的是context爲咱們提供了兩個方法來獲取輸入輸出流。

四.SharedPreferences
    1.什麼是SharedPreferences
        是一個鍵值對結構的容器, 相似於Map(Properties), 能夠向其中存儲鍵值對, 根據鍵查找值, 存儲在容器中的數據會以xml文件形式保存.
    2.怎麼使用
        使用Context.getSharedPreferences(String, int)獲取對象, 指定文件名和文件模式
        使用SharedPreferences.edit()方法獲取編輯器Editor
        使用Editor.putString(), putInt()等方法存儲數據
        使用Editor.commit()方法提交修改(相似事務)
        獲取的時候直接使用 SharedPreferences.getString(), getInt()等方法獲取數據ide

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="vertical" >

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="姓名" />
    <EditText
        android:id="@+id/nameET"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
         >
        <requestFocus />
    </EditText>

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="電話" />
    <EditText
        android:id="@+id/phoneET"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
         />

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="郵箱" />
    <EditText
        android:id="@+id/emailET"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
         />

    <Button
        android:id="@+id/button1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:onClick="onClick"
        android:text="保存爲默認" />
    
</LinearLayout>
activity_main.xml
package com.shellway.sp;

import android.support.v7.app.ActionBarActivity;
import android.content.SharedPreferences;
import android.content.SharedPreferences.Editor;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.EditText;

public class MainActivity extends ActionBarActivity {

    private EditText nameET;
    private EditText phoneET;
    private EditText emailET;
    private SharedPreferences sp;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        //獲取文本信息
        nameET = (EditText) findViewById(R.id.nameET);
        phoneET = (EditText) findViewById(R.id.phoneET);
        emailET = (EditText) findViewById(R.id.emailET);
        //獲取對象,默認指定當前應用,文件名爲data.xml.模式爲私有
        sp = getSharedPreferences("data", MODE_PRIVATE);
        nameET.setText(sp.getString("name", ""));
        phoneET.setText(sp.getString("phone", ""));
        emailET.setText(sp.getString("email", ""));
    }
    
    public void onClick(View view){
        String name = nameET.getText().toString();
        String phone = phoneET.getText().toString();
        String email = emailET.getText().toString();
        Editor editor = sp.edit();//獲取編輯器
        editor.putString("name", name);//存儲數據(還沒進入文件)
        editor.putString("phone", phone);
        editor.putString("email", email);
        editor.commit(); //提交修改(相似事務)     
    }
}
MainActivity.java

       
五.XML
    1.解析
        獲取解析器: Xml.newPullParser()
        設置輸入流: parser.setInput(InputStream, String)
        獲取當前事件類型: parser.getEventType(), 共5種
        獲取下一個事件類型: parser.next()
        獲取標籤名: parser.getName()
        獲取屬性值: parser.getAttributeValue(int)
        獲取下一個文本: parser.nextText()
    2.生成
        獲取解析器:
        設置輸出流:
        開始文檔:
        結束文檔:
        開啓標籤:
        結束標籤:
        設置屬性:
        設置文本:函數

練習:

<?xml version='1.0' encoding='UTF-8' standalone='yes' ?>
<persons>
    <person id="1">
        <name>范冰冰</name>
        <age>31</age>
    </person>
    <person id="2">
        <name>林志玲</name>
        <age>38</age>
    </person>
    <person id="3">
        <name>楊冪</name>
        <age>26</age>
    </person>
</persons>
persons.xml
package com.shellway.xml;

public class Persons {
     private Integer id;
     private String name;
     private Integer age;
     
    public Persons() {
        super();
    }
    
    public Persons(Integer id, String name, Integer age) {
        super();
        this.id = id;
        this.name = name;
        this.age = age;
    }

    public Integer getId() {
        return id;
    }
    public void setId(Integer id) {
        this.id = id;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public Integer getAge() {
        return age;
    }
    public void setAge(Integer age) {
        this.age = age;
    }

    @Override
    public String toString() {
        return "Persons [id=" + id + ", name=" + name + ", age=" + age + "]";
    }
}
persons.java
package com.shellway.xml;

import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;

import org.xmlpull.v1.XmlPullParser;
import org.xmlpull.v1.XmlPullParserException;
import org.xmlpull.v1.XmlSerializer;

import android.util.Xml;

public class PersonService {
    
    public List<Persons> loadPerson(InputStream in) throws Exception{
        List<Persons> list = new ArrayList<Persons>();
        XmlPullParser paser = Xml.newPullParser();
        paser.setInput(in, "utf-8");
        Persons p = null;
        for (int type =paser.getEventType(); type!=XmlPullParser.END_DOCUMENT; type=paser.next()) {
            if (type == XmlPullParser.START_TAG) {
                if (paser.getName().equals("person")) {
                    p = new Persons();
                    String id = paser.getAttributeValue(null, "id");
                    p.setId(Integer.parseInt(id));
                    list.add(p);
                } else if (paser.getName().equals("name")) {
                    String name = paser.nextText();
                    p.setName(name);
                }else if (paser.getName().equals("age")) {
                    String age = paser.nextText();
                    p.setAge(Integer.parseInt(age));
                }
                
            }
        }
        
        return list;
    }

    public void savePerson(List<Persons> persons,FileOutputStream fileOutputStream) throws Exception {
        
        XmlSerializer xmlSerializer = Xml.newSerializer();
        xmlSerializer.setOutput(fileOutputStream, "utf-8");
        xmlSerializer.startDocument("utf-8", true);
        xmlSerializer.startTag(null, "persons");
        for (Persons p : persons) {
            xmlSerializer.startTag(null, "person");
            xmlSerializer.attribute(null, "id", p.getId().toString());
            xmlSerializer.endTag(null, "person");
            
            xmlSerializer.startTag(null, "name");
            xmlSerializer.text(p.getName());
            xmlSerializer.endTag(null, "name");
            
            xmlSerializer.startTag(null, "age");
            xmlSerializer.text(p.getAge().toString());
            xmlSerializer.endTag(null, "age");
        }
        xmlSerializer.endTag(null, "persons");
        xmlSerializer.endDocument();
    }
}
PersonService.java
package com.shellway.xml;

import java.io.FileOutputStream;
import java.io.InputStream;
import java.util.List;

import android.test.AndroidTestCase;

public class TestPerson extends AndroidTestCase {
     public void testLoad() throws Exception{
         PersonService personService = new PersonService();
         InputStream in = this.getClass().getClassLoader().getResourceAsStream("persons.xml");
         List<Persons> persons = personService.loadPerson(in);
         for (Persons person : persons) {
            System.out.println(person); 
        }
         
        Persons person = new Persons(4,"shellway",25);
        persons.add(person);
        personService.savePerson(persons,new FileOutputStream("/mnt/sdcard/person.xml") );
        
     }
}
TestPerson.java
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.shellway.xml"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
        android:minSdkVersion="8"
        android:targetSdkVersion="21" />
    
        <instrumentation
        android:targetPackage="com.shellway.xml"
        android:name="android.test.InstrumentationTestRunner" />
        <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
     <uses-library android:name="android.test.runner" />
        <activity
            android:name=".MainActivity"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>
AndroidManifest.xml


六.SQLite數據庫
    1.SQLite數據庫的特色
        手機自帶的數據庫, 不區分數據類型(除了主鍵), 語法和MySQL相同, 每一個庫是一個文件
    2.建立庫
        定義類繼承SQLiteOpenHelper, 定義構造函數, 顯式調用父類構造函數, 傳入4個參數
        重寫onCreate()和onUpgrade()方法
        調用getWritableDatabase()或者getReadableDatabase()方法均可以建立數據庫
        數據庫文件不存在時, 會建立數據庫文件, 而且執行onCreate()方法
        數據庫文件存在, 而且版本沒有改變時, 不執行任何方法
        數據庫文件存在, 版本提高, 執行onUpgrade()方法
    3.增刪改查
        增刪改均可以使用SQLiteDatabase.execSQL()方法執行SQL語句完成
        查詢方法須要使用SQLiteDatabase.rawQuery()方法進行查詢, 獲得一個Cursor, 再調用moveToNext()和getString()getInt()等方法獲取數據

package com.shellway.sqlite;

import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;

public class DBSQLiteHelper extends SQLiteOpenHelper {
    public DBSQLiteHelper(Context context){
        super(context,"data.db" , null, 4);
        /**
         * 因爲弗雷沒有無參的構造函數,必須顯式調用有參的構造函數
         * 參數1:上下文環境,用來肯定數據庫文件存儲的目錄
         * 參數2:數據庫文件的名字
         * 參數3:生成遊標的工廠,填null就是使用默認的
         * 參數4:數據庫的版本,從1開始
         */
    }

    @Override
    public void onCreate(SQLiteDatabase db) {
      System.out.println("onCreate");
      db.execSQL("CREATE TABLE people(id INTEGER PRIMARY KEY AUTOINCREMENT,name VACHAR(20))");
    }

    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
     System.out.println("onUpgrade");
     db.execSQL("ALTER TABLE people ADD balance INTEGER");
    }
}
DBSQLiteHelper
package com.shellway.sqlite;

public class Person {
    
    private Integer id;
    private String name;
    private Integer balance;
    public Person() {
        super();
    }
    public Person(String name, Integer balance) {
        super();
        this.name = name;
        this.balance = balance;
    }
    public Person(Integer id, String name, Integer balance) {
        super();
        this.id = id;
        this.name = name;
        this.balance = balance;
    }
    public Integer getId() {
        return id;
    }
    public void setId(Integer id) {
        this.id = id;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public Integer getBalance() {
        return balance;
    }
    public void setBalance(Integer balance) {
        this.balance = balance;
    }
    @Override
    public String toString() {
        return "person [id=" + id + ", name=" + name + ", balance=" + balance
                + "]";
    }
}
Person
package com.shellway.sqlite;

import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;

public class PersonDAO {
    private DBSQLiteHelper helper;
    
    public PersonDAO(Context context) {
        helper = new DBSQLiteHelper(context);
    }
    
    public void insert(Person p){
         SQLiteDatabase db = helper.getWritableDatabase();//獲取數據庫連接(可寫的)
         db.execSQL("INSERT INTO people(name,balance) VALUES(?,?)", new Object[]{p.getName(),p.getBalance()} );
         db.close();
    }
    public void delete(Integer id){
        SQLiteDatabase db = helper.getWritableDatabase();
        db.execSQL("DELETE FROM people WHERE id = ?", new Object[]{id});
        db.close();
    }
    public void update(Person p){
        SQLiteDatabase db = helper.getWritableDatabase();
        db.execSQL("update people set name=?,balance=? where id=? ", new Object[]{p.getName(),p.getBalance(),p.getId()});
        db.close();
    }
    public Person query(Integer id){
        /**
         * 查詢時候應該優先使用getReadableDatabase()而不是getWritableDatabase(),
         * 其實getReadableDatabase是先獲取getWritableDatabase,若獲取失敗則採用getReadableDatabase
         */
        SQLiteDatabase db = helper.getReadableDatabase();
        Cursor c = db.rawQuery("select name,balance from people where id=?",new String[]{id+""});
        Person p = null ;
        if (c.moveToNext()) {
            String name = c.getString(c.getColumnIndex("name"));
            int balance = c.getInt(1);//若直接用下標方式,則注意該字段的索引,遊標的索引是從0開始的
            p = new Person(id,name,balance);
        }
        c.close();
        db.close();
        return p;
    }
}
PersonDAO
package com.shellway.sqlite;

import android.database.sqlite.SQLiteDatabase;
import android.provider.SyncStateContract.Helpers;
import android.test.AndroidTestCase;

public class TestSQLite extends AndroidTestCase {
     public void test1(){
         DBSQLiteHelper helper = new DBSQLiteHelper(getContext());
         SQLiteDatabase sql = helper.getWritableDatabase();
         /**
          * 獲取可寫的數據庫鏈接
          * 數據庫文件不存在時,會建立數據庫文件,而且執行onCreate()方法
          * 數據庫文件存在,且版本沒有改變時,不執行任何方法
          * 數據庫文件存在,版本提高,執行onUpdate方法
          */
     }
     public void testInsert(){
         PersonDAO personDAO = new PersonDAO(getContext());
         personDAO.insert(new Person("Jerry",20000));
     }
     public void testDelete(){
         PersonDAO personDAO = new PersonDAO(getContext());
         personDAO.delete(2);
     }
     public void testUpdate(){
         PersonDAO personDAO = new PersonDAO(getContext());
         personDAO.update(new Person(1,"www",30000));
     }
     public void testQuery(){
         PersonDAO personDAO = new PersonDAO(getContext());
         System.out.println(personDAO.query(1));
     }
}
TestSQLite
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.shellway.sqlite"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
        android:minSdkVersion="8"
        android:targetSdkVersion="21" />
        <instrumentation
        android:targetPackage="com.shellway.sqlite"
        android:name="android.test.InstrumentationTestRunner" />
    
    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
     <uses-library android:name="android.test.runner" />
        <activity
            android:name=".MainActivity"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>
AndroidManifest.xml

 

查詢全部, 查詢個數, 查詢翻頁:

package com.shellway.sqlite;

import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;

public class DBSQLiteHelper extends SQLiteOpenHelper {
    public DBSQLiteHelper(Context context){
        super(context,"data.db" , null, 4);
        /**
         * 因爲弗雷沒有無參的構造函數,必須顯式調用有參的構造函數
         * 參數1:上下文環境,用來肯定數據庫文件存儲的目錄
         * 參數2:數據庫文件的名字
         * 參數3:生成遊標的工廠,填null就是使用默認的
         * 參數4:數據庫的版本,從1開始
         */
    }

    @Override
    public void onCreate(SQLiteDatabase db) {
      System.out.println("onCreate");
      db.execSQL("CREATE TABLE people(id INTEGER PRIMARY KEY AUTOINCREMENT,name VACHAR(20))");
    }

    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
     System.out.println("onUpgrade");
     db.execSQL("ALTER TABLE people ADD balance INTEGER");
    }
}
DBSQLiteHelper
package com.shellway.sqlite;

public class Person {
    
    private Integer id;
    private String name;
    private Integer balance;
    public Person() {
        super();
    }
    public Person(String name, Integer balance) {
        super();
        this.name = name;
        this.balance = balance;
    }
    public Person(Integer id, String name, Integer balance) {
        super();
        this.id = id;
        this.name = name;
        this.balance = balance;
    }
    public Integer getId() {
        return id;
    }
    public void setId(Integer id) {
        this.id = id;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public Integer getBalance() {
        return balance;
    }
    public void setBalance(Integer balance) {
        this.balance = balance;
    }
    @Override
    public String toString() {
        return "person [id=" + id + ", name=" + name + ", balance=" + balance
                + "]";
    }
}
Person
package com.shellway.sqlite;

import java.util.ArrayList;
import java.util.List;

import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;

public class PersonDAO {
    private DBSQLiteHelper helper;
    
    public PersonDAO(Context context) {
        helper = new DBSQLiteHelper(context);
    }
    
    public void insert(Person p){
         SQLiteDatabase db = helper.getWritableDatabase();//獲取數據庫連接(可寫的)
         db.execSQL("INSERT INTO people(name,balance) VALUES(?,?)", new Object[]{p.getName(),p.getBalance()} );
         db.close();
    }
    public void delete(Integer id){
        SQLiteDatabase db = helper.getWritableDatabase();
        db.execSQL("DELETE FROM people WHERE id = ?", new Object[]{id});
        db.close();
    }
    public void update(Person p){
        SQLiteDatabase db = helper.getWritableDatabase();
        db.execSQL("update people set name=?,balance=? where id=? ", new Object[]{p.getName(),p.getBalance(),p.getId()});
        db.close();
    }
    //根據id查詢某條記錄
    public Person query(Integer id){
        /**
         * 查詢時候應該優先使用getReadableDatabase()而不是getWritableDatabase(),
         * 其實getReadableDatabase是先獲取getWritableDatabase,若獲取失敗則採用getReadableDatabase
         */
        SQLiteDatabase db = helper.getReadableDatabase();
        Cursor c = db.rawQuery("select name,balance from people where id=?",new String[]{id+""});
        Person p = null ;
        if (c.moveToNext()) {
            String name = c.getString(c.getColumnIndex("name"));
            int balance = c.getInt(1);//若直接用下標方式,則注意該字段的索引,遊標的索引是從0開始的
            p = new Person(id,name,balance);
        }
        c.close();
        db.close();
        return p;
    }
    //查詢所有記錄
    public List<Person> findAll(){
        SQLiteDatabase db = helper.getReadableDatabase();
        Cursor c = db.rawQuery("select id,name,balance from people", null);
        List<Person>  persons = new ArrayList<Person>();
        while (c.moveToNext()) {
            Person p = new Person(c.getInt(0),c.getString(1),c.getInt(2));
            persons.add(p);
        }
        c.close();
        db.close();
        return persons;
    }
    //查詢記錄總條數
    public int queryCount(){
        SQLiteDatabase db = helper.getReadableDatabase();
        Cursor c = db.rawQuery("select count(*) from people", null);
        c.moveToNext();
        int i = c.getInt(0);
        c.close();
        db.close();
        return i;
    }
    //分頁查詢
    public List<Person> queryPage(int pageNum,int capacity){
        String offset = (pageNum-1) * capacity +"";  //偏移量,便是第幾頁的頁數
        String len = capacity + "";                  //一頁中顯示的個數
        SQLiteDatabase db = helper.getReadableDatabase();
        Cursor c = db.rawQuery("select id,name,balance from people limit ?,?", new String[]{offset,len});
        List<Person>  persons = new ArrayList<Person>();
        while (c.moveToNext()) {
            Person p = new Person(c.getInt(0),c.getString(1),c.getInt(2));
            persons.add(p);
        }
        c.close();
        db.close();
        return persons;
    }
}
PersonDAO
package com.shellway.sqlite;

import java.util.ArrayList;
import java.util.List;
import java.util.Random;

import android.database.sqlite.SQLiteDatabase;
import android.provider.SyncStateContract.Helpers;
import android.test.AndroidTestCase;

public class TestSQLite extends AndroidTestCase {
     public void test1(){
         DBSQLiteHelper helper = new DBSQLiteHelper(getContext());
         SQLiteDatabase sql = helper.getWritableDatabase();
         /**
          * 獲取可寫的數據庫鏈接
          * 數據庫文件不存在時,會建立數據庫文件,而且執行onCreate()方法
          * 數據庫文件存在,且版本沒有改變時,不執行任何方法
          * 數據庫文件存在,版本提高,執行onUpdate方法
          */
     }
     public void testInsert(){
         PersonDAO personDAO = new PersonDAO(getContext());
        // personDAO.insert(new Person("Jerry",20000));
         for (int i = 1; i <=100; i++) {
            personDAO.insert(new Person("Test"+i,new Random().nextInt(10000)));
        }
     }
     public void testDelete(){
         PersonDAO personDAO = new PersonDAO(getContext());
         personDAO.delete(2);
     }
     public void testUpdate(){
         PersonDAO personDAO = new PersonDAO(getContext());
         personDAO.update(new Person(1,"www",30000));
     }
     public void testQuery(){
         PersonDAO personDAO = new PersonDAO(getContext());
         System.out.println(personDAO.query(1));
     }
     public void testFindAll(){
         PersonDAO personDAO = new PersonDAO(getContext());
         List<Person> persons = personDAO.findAll();
         for (Person p : persons) {
            System.out.println(p);
        }
     }
     public void testQueryCount(){
         PersonDAO personDAO = new PersonDAO(getContext());
         int count = personDAO.queryCount();
         System.out.println(count);
     }
     public void testQueryPage(){
         PersonDAO personDAO = new PersonDAO(getContext());
         List<Person> persons = personDAO.queryPage(3, 20);
         for (Person p : persons) {
            System.out.println(p);
        }
     }
     
}
TestSQLite
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.shellway.sqlite"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
        android:minSdkVersion="8"
        android:targetSdkVersion="21" />
        <instrumentation
        android:targetPackage="com.shellway.sqlite"
        android:name="android.test.InstrumentationTestRunner" />
    
    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
     <uses-library android:name="android.test.runner" />
        <activity
            android:name=".MainActivity"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>
AndroidManifest.xml

查詢分頁結果:

相關文章
相關標籤/搜索