• $《第一行代码:Android》读书笔记——第6章 数据持久化


      主要讲述了Android数据持久化的三种方式:文件存储、SharedPreference存储、SQLite数据库存储。

    (一)文件存储

      其实Android中文件存储方式和Java的文件操作类似,就是用IO流进行操作。文件存储只能保存简单的字符串或二进制数据,不适合保存结构较为复杂的数据。

      1、示例程序(代码中有详细注释):

      (1)xml文件:

      其中有一个EditText,可以在里面输入字符,还有两个Button,一个用于保存输入的内容到一个文件中,另一个用于载入相应的文件内容到EditText中。

     1 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
     2     android:layout_width="match_parent"
     3     android:layout_height="match_parent"
     4     android:orientation="vertical" >
     5 
     6     <EditText
     7         android:id="@+id/input_et"
     8         android:layout_width="match_parent"
     9         android:layout_height="wrap_content" />
    10 
    11     <Button
    12         android:id="@+id/save_btn"
    13         android:layout_width="match_parent"
    14         android:layout_height="wrap_content"
    15         android:text="保存" />
    16 
    17 
    18     <Button
    19         android:id="@+id/load_btn"
    20         android:layout_width="match_parent"
    21         android:layout_height="wrap_content"
    22         android:text="载入文件内容" />
    23 
    24 </LinearLayout>

      (2)MainActivity:

      1 import java.io.BufferedReader;
      2 import java.io.BufferedWriter;
      3 import java.io.FileInputStream;
      4 import java.io.FileOutputStream;
      5 import java.io.InputStreamReader;
      6 import java.io.OutputStreamWriter;
      7 
      8 import android.app.Activity;
      9 import android.content.Context;
     10 import android.os.Bundle;
     11 import android.text.TextUtils;
     12 import android.view.Menu;
     13 import android.view.MenuItem;
     14 import android.view.View;
     15 import android.view.View.OnClickListener;
     16 import android.widget.Button;
     17 import android.widget.EditText;
     18 import android.widget.Toast;
     19 
     20 public class MainActivity extends Activity implements OnClickListener {
     21 
     22     private String dataFileName = "MyDataFile";
     23 
     24     private EditText inputEt;
     25     private Button saveBtn;
     26     private Button loadBtn;
     27 
     28     @Override
     29     protected void onCreate(Bundle savedInstanceState) {
     30         super.onCreate(savedInstanceState);
     31         setContentView(R.layout.activity_main);
     32 
     33         inputEt = (EditText) findViewById(R.id.input_et);
     34         saveBtn = (Button) findViewById(R.id.save_btn);
     35         loadBtn = (Button) findViewById(R.id.load_btn);
     36 
     37         saveBtn.setOnClickListener(this);
     38         loadBtn.setOnClickListener(this);
     39     }
     40 
     41     @Override
     42     public void onClick(View v) {
     43         switch (v.getId()) {
     44         case R.id.save_btn:
     45             String inputText = inputEt.getText().toString();
     46             if (inputText.length() == 0) {
     47                 Toast.makeText(MainActivity.this, "未输入任何内容!",
     48                         Toast.LENGTH_SHORT).show();
     49             } else {
     50                 save(dataFileName, inputText);
     51                 Toast.makeText(MainActivity.this, "保存成功!", Toast.LENGTH_SHORT)
     52                         .show();
     53             }
     54             break;
     55 
     56         case R.id.load_btn:
     57             String fileContent = load(dataFileName);
     58 
     59             // 用于判断一个字符串是否是null或者空内容的工具方法
     60             if (!TextUtils.isEmpty(fileContent)) {
     61                 inputEt.setText(fileContent);
     62                 // 让光标移到文字最后
     63                 inputEt.setSelection(fileContent.length());
     64                 Toast.makeText(this, "载入文件内容成功!", Toast.LENGTH_SHORT).show();
     65             }
     66             break;
     67         default:
     68             break;
     69         }
     70     }
     71 
     72     // 保存输入内容到文件的方法
     73     public void save(String fileName, String inputText) {
     74         FileOutputStream out = null;
     75         BufferedWriter writer = null;
     76 
     77         try {
     78             // 1.用Context类的openFileOutput方法创建FileOutputStream实例
     79             // MODE_PRIVATE模式是默认操作模式,表示当指定同样文件名时,所写入的内容将会覆盖原来的内容
     80             // MODE_APPEND表示如果该文件已经存在就往文件里面追加内容,不存在就创建新文件
     81             // 注:这里的文件名不可以包含路径,因为所有的文件都是默认存储到/data/data/包名/files目录的
     82             out = openFileOutput(fileName, Context.MODE_PRIVATE);
     83 
     84             // 2.用FileOutputStream实例创建OutputStreamWriter实例,再用OutputStreamWriter实例创建BufferedWriter实例
     85             writer = new BufferedWriter(new OutputStreamWriter(out));
     86 
     87             // 3.写入内容到文件
     88             writer.write(inputText);
     89 
     90             /**
     91              * 注:查看该文件的方法: DDMS—>File
     92              * Explorer—>/data/data/com.example.filepersistencetest(包名)/files/
     93              * 该目录下即可看到刚刚保存的文件,DDMS按钮下方有一个导出文件,即可把文件导出到电脑上用记事本查看
     94              */
     95 
     96         } catch (Exception e) {
     97             e.printStackTrace();
     98         } finally {
     99             try {
    100                 if (writer != null) {
    101                     writer.close();
    102                 }
    103             } catch (Exception e) {
    104                 e.printStackTrace();
    105             }
    106         }
    107     }
    108 
    109     // 载入并读取文件内容的方法
    110     public String load(String fileName) {
    111         FileInputStream in = null;
    112         BufferedReader reader = null;
    113         StringBuilder content = new StringBuilder();
    114 
    115         try {
    116             // 1.用Context类的openFileInput方法创建FileInputStream实例
    117             in = openFileInput(fileName);
    118 
    119             if (in == null) {
    120                 Toast.makeText(MainActivity.this, "数据文件不存在!",
    121                         Toast.LENGTH_SHORT).show();
    122                 return "";
    123             }
    124 
    125             // 2.创建BufferedReader实例
    126             reader = new BufferedReader(new InputStreamReader(in));
    127 
    128             String line = "";
    129 
    130             // 3.读取每一行
    131             while ((line = reader.readLine()) != null) {
    132                 content.append(line);
    133             }
    134         } catch (Exception e) {
    135             e.printStackTrace();
    136         } finally {
    137             if (reader != null) {
    138                 try {
    139                     reader.close();
    140                 } catch (Exception e) {
    141                     e.printStackTrace();
    142                 }
    143             }
    144         }
    145 
    146         return content.toString();
    147     }
    148 
    149     @Override
    150     protected void onDestroy() {
    151         super.onDestroy();
    152         String inputText = inputEt.getText().toString();
    153         if (inputText.length() != 0) {
    154             save(dataFileName, inputText);
    155         }
    156     }
    157 
    158 }

      2、用openFileOutput和openFileInput创建文件时,参数中的文件名不可以包含路径,因为所有的文件都是默认存储到/data/data/包名/files目录的。

      3、查看该文件的方法: DDMS—>File Explorer—>/data/data/com.example.filepersistencetest(包名)/files/,该目录下即可看到刚刚保存的文件,DDMS按钮下方有一个导出文件按钮,即可把文件导出到电脑上用记事本查看。

    (二)SharedPreferences

      SharedPreferences用键值对形式存储数据,适合保存程序的一些偏好设置等。SharedPreferences文件会自动存放在/data/data/包名/shared_prefs目录下,是xml格式的文件。

      1、获取SharedPreferences对象的三种方法:

      (1)Activity类的getPreferences方法,只接收一个模式参数,这个方法会自动把当前活动类名作为SharedPreferences文件名。
      (2)PreferencesManager类中的getDefaultSharedPreferences方法,这是一个静态方法,接收一个Context参数,并自动使用当前 应用程序的包名作为前缀来命名SharedPreferences文件。

      (3)Context类的getSharedPreferences方法,接受两个参数,第一个为文件名字符串(不要带路径!),第二个是文件操作模式。

      2、向SharedPreferences文件写入数据的步骤:

      (1)用SharedPreferences对象的edit方法获取SharedPreferences.Editor实例:

    1 SharedPreferences.Editor editor = getSharedPreferences("dataFile",
    2                 MODE_PRIVATE).edit();

      (2)写入数据到SharedPreferences中:

    1 editor.putString("name", "贾永基");
    2 editor.putInt("age", 23);
    3 editor.putBoolean("married", false);

      (3)用commit方法提交:

    1 editor.commit();

      3、从SharedPreferences文件读数据的步骤:

      (1)创建SharedPreferences实例:

    1 SharedPreferences pref = getSharedPreferences("dataFile", MODE_PRIVATE);

      (2)用getXXX方法读取数据:

    1      // 第一个参数表示键名,第二个参数表示如果找不到数据时候返回的默认值
    2         String name = pref.getString("name", "");
    3         int age = pref.getInt("age", 0);
    4         boolean married = pref.getBoolean("married", false);
    5 
    6         Log.d("MainActivity", "name is " + name);
    7         Log.d("MainActivity", "age is " + age);
    8         Log.d("MainActivity", "married is " + married);

      4、示例程序:

      (1)XML文件:

     1 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
     2     android:layout_width="match_parent"
     3     android:layout_height="match_parent"
     4     android:orientation="vertical" >
     5 
     6     <Button
     7         android:id="@+id/save_data_btn"
     8         android:layout_width="match_parent"
     9         android:layout_height="wrap_content"
    10         android:text="保存数据" />
    11 
    12     <Button
    13         android:id="@+id/load_data_btn"
    14         android:layout_width="match_parent"
    15         android:layout_height="wrap_content"
    16         android:text="载入数据" />
    17 
    18 </LinearLayout>

      (2)MainActivity:

     1 package com.example.sharedpreferencestest;
     2 
     3 import android.app.Activity;
     4 import android.content.SharedPreferences;
     5 import android.os.Bundle;
     6 import android.util.Log;
     7 import android.view.Menu;
     8 import android.view.MenuItem;
     9 import android.view.View;
    10 import android.view.View.OnClickListener;
    11 import android.widget.Button;
    12 import android.widget.Toast;
    13 
    14 public class MainActivity extends Activity implements OnClickListener {
    15 
    16     private Button saveDataBtn;
    17     private Button loadDataBtn;
    18 
    19     @Override
    20     protected void onCreate(Bundle savedInstanceState) {
    21         super.onCreate(savedInstanceState);
    22         setContentView(R.layout.activity_main);
    23 
    24         saveDataBtn = (Button) findViewById(R.id.save_data_btn);
    25         loadDataBtn = (Button) findViewById(R.id.load_data_btn);
    26 
    27         saveDataBtn.setOnClickListener(this);
    28         loadDataBtn.setOnClickListener(this);
    29     }
    30 
    31     @Override
    32     public void onClick(View v) {
    33         switch (v.getId()) {
    34         case R.id.save_data_btn:
    35             saveData();
    36             Toast.makeText(MainActivity.this, "保存数据成功", Toast.LENGTH_SHORT)
    37                     .show();
    38             break;
    39         case R.id.load_data_btn:
    40             loadData();
    41             break;
    42         default:
    43             break;
    44         }
    45     }
    46 
    47     // 保存数据到SharedPreferences
    48     public void saveData() {
    49         // 1.用SharedPreferences对象的edit方法获取SharedPreferences.Editor实例
    50         SharedPreferences.Editor editor = getSharedPreferences("dataFile",
    51                 MODE_PRIVATE).edit();
    52 
    53         // 注:获取SharedPreferences对象还有两种方法:
    54         // (1)Activity类的getPreferences方法,只接收一个模式参数,这个方法会自动把当前活动类名作为SharedPreferences文件名
    55         // (2)PreferencesManager类中的getDefaultSharedPreferences方法,这是一个静态方法,接收一个Context参数,并自动使用当前
    56         // 应用程序的包名作为前缀来命名SharedPreferences文件
    57 
    58         // 2.写入数据到SharedPreferences中
    59         editor.putString("name", "贾永基");
    60         editor.putInt("age", 23);
    61         editor.putBoolean("married", false);
    62 
    63         // 3.用commit方法提交
    64         // 注:SharedPreferences文件会自动存放在/data/data/包名/shared_prefs目录下,是xml格式的文件
    65         editor.commit();
    66     }
    67 
    68     // 从SharedPreferences读数据
    69     public void loadData() {
    70         SharedPreferences pref = getSharedPreferences("dataFile", MODE_PRIVATE);
    71 
    72         // 第一个参数表示键名,第二个参数表示如果找不到数据时候返回的默认值
    73         String name = pref.getString("name", "");
    74         int age = pref.getInt("age", 0);
    75         boolean married = pref.getBoolean("married", false);
    76 
    77         Log.d("MainActivity", "name is " + name);
    78         Log.d("MainActivity", "age is " + age);
    79         Log.d("MainActivity", "married is " + married);
    80     }
    81 
    82 }

     (三)SQLite

      SQLite是Android内嵌的轻量级关系型数据库,速度很快,支持标准的SQL语法,还支持ACID事务。

      1、创建数据库:

      继承SQLiteOpenHelper类创建自己的类MyDatabaseHelper,并实现onCreate和onUpgrade两个抽象方法,在onCreate方法中建表,在onUpgrade中升级数据库。

     1 import android.content.Context;
     2 import android.database.sqlite.SQLiteDatabase;
     3 import android.database.sqlite.SQLiteDatabase.CursorFactory;
     4 import android.database.sqlite.SQLiteOpenHelper;
     5 import android.widget.Toast;
     6 
     7 public class MyDatabaseHelper extends SQLiteOpenHelper {
     8 
     9     // 1.将建表语句定义成字符串常量
    10     public static final String CREATE_BOOK = "create table book(" // 注:表名和字段名称不区分大小写
    11             + "id integer primary key autoincrement,"
    12             + "author text,"
    13             + "price real," + "pages integer," + "name text,"+ "category_id integer)";;
    14 
    15     public static final String CREATE_CATEGORY = "create table category("
    16             + "id integer primary key autoincrement," + "category_name text,"
    17             + "category_code integer)";
    18 
    19     private Context mContext;
    20 
    21     public MyDatabaseHelper(Context context, String name,
    22             CursorFactory factory, int version) {
    23         super(context, name, factory, version);
    24         mContext = context;
    25     }
    26 
    27     @Override
    28     public void onCreate(SQLiteDatabase db) {
    29         // 2.用SQLiteDatabase的execSQL方法执行建表语句
    30         db.execSQL(CREATE_BOOK);
    31         db.execSQL(CREATE_CATEGORY);
    32 
    33         Toast.makeText(mContext, "创建数据库成功!", Toast.LENGTH_SHORT).show();
    34     }
    35 
    36     @Override
    37     public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
    38         switch (oldVersion) {
    39         case 1:
    40             db.execSQL(CREATE_CATEGORY);
    41         case 2: // 注意这里case的最后是不写break的,以应对跨版本升级的情况
    42             db.execSQL("alter table book add column category_id integer");
    43         default:
    44             break;
    45         }
    46     }
    47 
    48 }

      2、创建数据库后,在adb shell中可以用命令行方式查看数据库的具体数据,方法如下:

      (1)打开控制台窗口,输入adb shell,然后cd到路径:/data/data/当前包名/databases/,使用ls查看当前目录里的文件。

      (2)假设提前创建的数据库名叫BookStore.db,那么接着就用sqlite3 BookStore.db命令打开数据库,然后可以输入各种SQL语句进行操作。

      (3)输入.table命令可以查看当前数据库的表,.schema命令可以查看所有表的建表语句。.exit或.quit命令可以退出数据库编辑,exit命令可以退出adb shell。

      (4)在数据库中查询结果出现乱码的情况的解决(Win7环境):

      在控制台里输入命令:chcp 65001 确定—>在命令行标题栏上点击右键,选择【属性】 -【字体】,将字体修改为【Lucida Console】 确定
      完成后再通过 adb shell 进入sqlite3,乱码解决.
      注:恢复cmd的默认设置:Win+R -> 输入regedit -> 找到HKEY_CURRENT_USERConsole\%SystemRoot%_system32_cmd.exe -> 右键删除文件夹%SystemRoot%_system32_cmd.exe -> 重启cmd即可。

      3、示例程序:

      (1)xml文件:

     1 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
     2     android:layout_width="match_parent"
     3     android:layout_height="match_parent"
     4     android:orientation="vertical" >
     5 
     6     <Button
     7         android:id="@+id/create_database_btn"
     8         android:layout_width="match_parent"
     9         android:layout_height="wrap_content"
    10         android:text="创建数据库" />
    11 
    12     <Button
    13         android:id="@+id/add_data_btn"
    14         android:layout_width="match_parent"
    15         android:layout_height="wrap_content"
    16         android:text="添加数据" />
    17 
    18     <Button
    19         android:id="@+id/update_data_btn"
    20         android:layout_width="match_parent"
    21         android:layout_height="wrap_content"
    22         android:text="更新数据" />
    23 
    24     <Button
    25         android:id="@+id/delete_data_btn"
    26         android:layout_width="match_parent"
    27         android:layout_height="wrap_content"
    28         android:text="删除数据" />
    29 
    30     <Button
    31         android:id="@+id/query_data_btn"
    32         android:layout_width="match_parent"
    33         android:layout_height="wrap_content"
    34         android:text="查询数据" />
    35 
    36     <TextView
    37         android:layout_width="match_parent"
    38         android:layout_height="wrap_content"
    39         android:text="查询结果:" />
    40 
    41     <TextView
    42         android:id="@+id/query_result_tv"
    43         android:layout_width="match_parent"
    44         android:layout_height="wrap_content" />
    45 
    46 </LinearLayout>

      (2)MainActivity:

      1 package com.example.databasetest2;
      2 
      3 import java.util.ArrayList;
      4 
      5 import android.app.Activity;
      6 import android.database.Cursor;
      7 import android.database.sqlite.SQLiteDatabase;
      8 import android.os.Bundle;
      9 import android.view.Menu;
     10 import android.view.MenuItem;
     11 import android.view.View;
     12 import android.view.View.OnClickListener;
     13 import android.widget.Button;
     14 import android.widget.EditText;
     15 import android.widget.TextView;
     16 
     17 public class MainActivity extends Activity implements OnClickListener {
     18 
     19     private Button createDatabaseBtn;
     20     private Button addDataBtn;
     21     private Button updateDataBtn;
     22     private Button deleteDataBtn;
     23     private Button queryDataBtn;
     24     private TextView queryResultTv;
     25 
     26     private MyDatabaseHelper dbHelper;
     27 
     28     @Override
     29     protected void onCreate(Bundle savedInstanceState) {
     30         super.onCreate(savedInstanceState);
     31         setContentView(R.layout.activity_main);
     32 
     33         // 1.创建MyDatabaseHelper实例
     34         dbHelper = new MyDatabaseHelper(this, "BookStore.db", null, 3); // 这里的3为数据库版本号
     35 
     36         createDatabaseBtn = (Button) findViewById(R.id.create_database_btn);
     37         addDataBtn = (Button) findViewById(R.id.add_data_btn);
     38         updateDataBtn = (Button) findViewById(R.id.update_data_btn);
     39         deleteDataBtn = (Button) findViewById(R.id.delete_data_btn);
     40         queryDataBtn = (Button) findViewById(R.id.query_data_btn);
     41         queryResultTv = (TextView) findViewById(R.id.query_result_tv);
     42 
     43         createDatabaseBtn.setOnClickListener(this);
     44         addDataBtn.setOnClickListener(this);
     45         updateDataBtn.setOnClickListener(this);
     46         deleteDataBtn.setOnClickListener(this);
     47         queryDataBtn.setOnClickListener(this);
     48     }
     49 
     50     @Override
     51     public void onClick(View v) {
     52         SQLiteDatabase db;
     53         switch (v.getId()) {
     54         case R.id.create_database_btn:
     55             // 2.调用MyDatabaseHelper的getWritableDatabase方法打开数据库
     56             dbHelper.getWritableDatabase();
     57             break;
     58         case R.id.add_data_btn:
     59             // 先获取SQLiteDatabase实例,然后直接用execSQL方法执行SQL语句的方式往表中插入数据
     60             db = dbHelper.getWritableDatabase();
     61             db.execSQL(
     62                     "insert into book (name,author,pages,price,category_id) values (?,?,?,?,?)",
     63                     new String[] { "三体", "刘慈欣", "567", "49.9", "1" }); // 注:所有类型的占位符数据都要是字符串,若语句中无占位符参数,则第二个函数参数可为null
     64             db.execSQL(
     65                     "insert into book (name,author,pages,price,category_id) values (?,?,?,?,?)",
     66                     new String[] { "第一行代码——Android", "郭霖", "401", "25.9", "3" });
     67             break;
     68         case R.id.update_data_btn:
     69             db = dbHelper.getWritableDatabase();
     70             // 更新数据
     71             db.execSQL("update book set price = ? where name = ?",
     72                     new String[] { "10.99", "三体" });
     73             break;
     74         case R.id.delete_data_btn:
     75             db = dbHelper.getWritableDatabase();
     76             // 删除数据
     77             db.execSQL("delete from book where pages > ?", new String[] { "1" });
     78             break;
     79         case R.id.query_data_btn:
     80             db = dbHelper.getWritableDatabase();
     81             Cursor cursor = db.rawQuery("select * from book where id < ?",
     82                     new String[] { "100" });
     83             int idIndex = 0;
     84             int authorIndex = 0;
     85             int priceIndex = 0;
     86             int pagesIndex = 0;
     87             int nameIndex = 0;
     88             int categoryIdIndex = 0;
     89 
     90             ArrayList<Book> bookQueryList = new ArrayList<Book>();
     91 
     92             // 获取每个字段的ColumnIndex
     93             if (cursor.getCount() >= 0) {
     94                 idIndex = cursor.getColumnIndex("id");
     95                 authorIndex = cursor.getColumnIndex("author");
     96                 priceIndex = cursor.getColumnIndex("price");
     97                 pagesIndex = cursor.getColumnIndex("pages");
     98                 nameIndex = cursor.getColumnIndex("name");
     99                 categoryIdIndex = cursor.getColumnIndex("category_id");
    100             }
    101             while (cursor.moveToNext()) {
    102                 Book book = new Book();
    103                 book.setId(cursor.getInt(idIndex));
    104                 book.setAuthor(cursor.getString(authorIndex));
    105                 book.setPrice(cursor.getDouble(priceIndex));
    106                 book.setPages(cursor.getInt(pagesIndex));
    107                 book.setName(cursor.getString(nameIndex));
    108                 book.setCategoryId(cursor.getInt(categoryIdIndex));
    109 
    110                 bookQueryList.add(book);
    111             }
    112 
    113             queryResultTv.setText(bookQueryList.toString());
    114             break;
    115         default:
    116             break;
    117         }
    118     }
    119 }
    120 
    121 // Book类
    122 class Book {
    123     private int id;
    124     private String author;
    125     private double price;
    126     private int pages;
    127     private String name;
    128     private int categoryId;
    129 
    130     public int getCategoryId() {
    131         return categoryId;
    132     }
    133 
    134     public void setCategoryId(int categoryId) {
    135         this.categoryId = categoryId;
    136     }
    137 
    138     public int getId() {
    139         return id;
    140     }
    141 
    142     public void setId(int id) {
    143         this.id = id;
    144     }
    145 
    146     public String getAuthor() {
    147         return author;
    148     }
    149 
    150     public void setAuthor(String author) {
    151         this.author = author;
    152     }
    153 
    154     public double getPrice() {
    155         return price;
    156     }
    157 
    158     public void setPrice(double price) {
    159         this.price = price;
    160     }
    161 
    162     public int getPages() {
    163         return pages;
    164     }
    165 
    166     public void setPages(int pages) {
    167         this.pages = pages;
    168     }
    169 
    170     public String getName() {
    171         return name;
    172     }
    173 
    174     public void setName(String name) {
    175         this.name = name;
    176     }
    177 
    178     @Override
    179     public String toString() {
    180         return "Book [ id = " + id + ", author = " + author + ", price = "
    181                 + price + ", pages = " + pages + ", name = " + name
    182                 + ", category_id = " + categoryId + " ]";
    183     }
    184 }

    程序运行效果:

      4、使用事务 

     1             // 删除旧数据并添加新数据,两个操作为一个原子操作
     2             SQLiteDatabase db = dbHelper.getWritableDatabase();
     3             db.beginTransaction(); // 开启事务
     4             try {
     5                 db.delete("book", null, null);
     6                 // if (true) {
     7                 // // 在这里手动抛出一个异常,让事务失败
     8                 // throw new NullPointerException();
     9                 // }
    10                 ContentValues values = new ContentValues();
    11                 values.put("name", "这是本新书");
    12                 values.put("author", "贾永基");
    13                 values.put("pages", 123);
    14                 values.put("price", 13.4);
    15                 db.insert("book", null, values);
    16                 db.setTransactionSuccessful();// 事务已经执行成功
    17 
    18             } catch (Exception e) {
    19                 e.printStackTrace();
    20             } finally {
    21                 db.endTransaction(); // 结束事务
    22             }

       5、补充:使用SQLiteDataBase类自带的方法进行数据库的增、删、改操作(因为使用自带的方法进行查询的操作过于复杂不做介绍,直接使用SQL语句即可):

      (1)插入数据:

     1 ...
     2 SQLiteDatabase db = dbHelper.getWritableDatabase();
     3 
     4 // 使用ContentValues对象组装数据
     5 ContentValues values = new ContentValues();
     6 values.put("name","三体");
     7 values.put("pages",565);
     8 values.put("price",23.99);
     9 
    10 // 插入数据到数据库中
    11 // 第一个参数:表名;第二个参数:用于在未指定添加数据的情况下为某些可为空的字段自动赋值为NULL,一般用不到这个功能,把这个参数传入null即可;第三个参数:携带数据的ContentValues对象
    12 db.insert("Book",null,values);
    13 ...
  • 相关阅读:
    探讨.net Socket支持在线连接数量
    Net Configuration Agent
    Http压力测试工具HttpTest4Net
    TCP连接有效性检测方法
    SocketAsyncEventArgs使用解说
    可靠、高吞吐架构基础改造
    PerformanceCounter蛋痛的设计
    谱聚类(spectral clustering)原理总结
    用scikit-learn学习DBSCAN聚类
    DBSCAN密度聚类算法
  • 原文地址:https://www.cnblogs.com/jiayongji/p/5319485.html
Copyright © 2020-2023  润新知