Room 让数据库变得无比高效简洁 2.一个简单的小例子的进阶和完善

介绍几个新东西

Async Task 把数据库的操作放到别的线程里,不能放在主线程

Repository  把数据库的内容放入View Model中,并引入LiveData

 

每次我们进行一步操作都得用我们自己写的UpdateView来刷新一下页面,LiveData就省去了我们这个烦恼

Room与LiveData+ViewModel结合使用

 

我们的MainActivity就应该专注于页面,自己写的类作为数据仓库,专注于对数据库的操作,ViewModel则是二者的桥梁。

依赖

def room_version = "2.2.0"

    implementation "androidx.room:room-runtime:$room_version"
    annotationProcessor "androidx.room:room-compiler:$room_version"
    implementation 'android.arch.lifecycle:extensions:1.1.1'
// optional - Test helpers
    testImplementation "androidx.room:room-testing:$room_version"
ViewModel等的依赖

 

 

 先写一下实体类

package com.example.roomtwo.dao;

import androidx.room.ColumnInfo;
import androidx.room.Entity;
import androidx.room.PrimaryKey;

//@Entity(tableName = "haha")   如果不指定表名,则表名跟类名同,大小写敏感
@Entity
public class Word {
    @PrimaryKey(autoGenerate = true)
    private int id;
    @ColumnInfo(name = "english_word")
    private String word;
    @ColumnInfo(name = "chinese_meaning")
    private String chineseMeaning;

    public Word(String word, String chineseMeaning) {
        this.word = word;
        this.chineseMeaning = chineseMeaning;
    }


    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getWord() {
        return word;
    }

    public void setWord(String word) {
        this.word = word;
    }

    public String getChineseMeaning() {
        return chineseMeaning;
    }

    public void setChineseMeaning(String chineseMeaning) {
        this.chineseMeaning = chineseMeaning;
    }

    @Override
    public String toString() {
        return "Word{" +
                "id=" + id +
                ", word='" + word + '\'' +
                ", chineseMeaning='" + chineseMeaning + '\'' +
                '}';
    }
}
Word.class

再写一下dao层接口

package com.example.roomtwo.dao;

import androidx.lifecycle.LiveData;
import androidx.room.Dao;
import androidx.room.Delete;
import androidx.room.Insert;
import androidx.room.Query;
import androidx.room.Update;

import java.util.List;

@Dao
public interface WordDao {

    @Insert
    void insertWords(Word...Word);

    @Update
    void updateWords(Word...Word);

    @Delete
    void deleteWords(Word...Word);

    @Query("delete from word")
    void deleteAllWords();

    @Query("select * from Word")
    List<Word> getAllWords();

    @Query("select * from Word")
    LiveData<List<Word>> getAllWordLiveData();

}
WordDao

写一下创建数据库相关的类

package com.example.roomtwo.dao;

import android.content.Context;

import androidx.annotation.NonNull;
import androidx.room.Dao;
import androidx.room.Database;
import androidx.room.DatabaseConfiguration;
import androidx.room.InvalidationTracker;
import androidx.room.Room;
import androidx.room.RoomDatabase;
import androidx.sqlite.db.SupportSQLiteOpenHelper;

//singleton
@Database(entities = Word.class,version = 1,exportSchema = false)
public abstract class WordDatabase extends RoomDatabase {

    //单例模式创建以及获取数据库的实例
    private static WordDatabase instance;
    public static synchronized WordDatabase getDatabase(Context context){
        if (instance == null){
            instance = Room.databaseBuilder(context.getApplicationContext(),WordDatabase.class,"fuck2.db")
                    .allowMainThreadQueries()
                    .build();
        }
        return instance;
    }

    public abstract WordDao getWordDao();

}
WordDatabase

专注于操作数据库的数据库仓库类

package com.example.roomtwo.dao;

import android.content.Context;
import android.os.AsyncTask;

import androidx.lifecycle.LiveData;

import java.util.List;

public class WordRepository {

    private WordDao wordDao;
    private WordDatabase wordDatabase;

    private LiveData<List<Word>> allWordLive;

    public WordRepository(Context context) {
        //创建数据库
        wordDatabase = WordDatabase.getDatabase(context.getApplicationContext());
        //获取dao层接口
        wordDao = wordDatabase.getWordDao();
        //得到可观察的数据
        allWordLive = wordDao.getAllWordLiveData();
    }

    public LiveData<List<Word>> getAllWordLive() {
        return allWordLive;
    }

    /********************使用下面那几个增删改查的接口,方便别人调用**************************/
    public void insertWords(Word...words){
        new WordRepository.InsertAsyncTask(wordDao).execute(words);
    }

    public void updateWords(Word...words){
        new WordRepository.UpdateAsyncTask(wordDao).execute(words);
    }

    public void deleteWords(Word...words){
        new WordRepository.DeleteAsyncTask(wordDao).execute(words);
    }

    public void deleteAllWords(Void...voids){
        new WordRepository.DeleteAllAsyncTask(wordDao).execute();
    }


    //数据库不能运行在主线程中,我们现在有增删改查四个操作,就得在外面创建四个AsyncTask类文件
    //为了方便,现在我们写成内部类
    static class InsertAsyncTask extends AsyncTask<Word,Void,Void> {

        private WordDao wordDao;

        //构造函数
        public InsertAsyncTask(WordDao wordDao) {
            this.wordDao = wordDao;
        }
        //在后台上做操作
        @Override
        protected Void doInBackground(Word... words) {
            wordDao.insertWords(words);
            return null;
        }
    }

    //更新
    static class UpdateAsyncTask extends AsyncTask<Word,Void,Void>{

        private WordDao wordDao;

        public UpdateAsyncTask(WordDao wordDao) {
            this.wordDao = wordDao;
        }
        //在后台上做操作
        @Override
        protected Void doInBackground(Word... words) {
            wordDao.updateWords(words);
            return null;
        }
    }

    //删除
    static class DeleteAsyncTask extends AsyncTask<Word,Void,Void>{

        private WordDao wordDao;

        public DeleteAsyncTask(WordDao wordDao) {
            this.wordDao = wordDao;
        }
        //在后台上做操作
        @Override
        protected Void doInBackground(Word... words) {
            wordDao.deleteWords(words);
            return null;
        }
    }

    //删除所有   没有参数就是Void
    static class DeleteAllAsyncTask extends AsyncTask<Void,Void,Void>{

        private WordDao wordDao;

        public DeleteAllAsyncTask(WordDao wordDao) {
            this.wordDao = wordDao;
        }

        //在后台上做操作
        @Override
        protected Void doInBackground(Void... voids) {
            wordDao.deleteAllWords();
            return null;
        }
    }
}
WordRepository

activity和数据的桥梁 ViewModel

package com.example.roomtwo;

import android.app.Application;
import android.os.AsyncTask;

import androidx.annotation.NonNull;
import androidx.lifecycle.AndroidViewModel;
import androidx.lifecycle.LiveData;
import androidx.lifecycle.ViewModelProvider;
import androidx.lifecycle.ViewModelProviders;

import com.example.roomtwo.dao.Word;
import com.example.roomtwo.dao.WordDao;
import com.example.roomtwo.dao.WordDatabase;
import com.example.roomtwo.dao.WordRepository;

import java.util.List;

public class WordViewModel extends AndroidViewModel {

    //数据仓库
    private WordRepository wordRepository;

    //可观察的数据
    private LiveData<List<Word>> allWordLive;

    public WordViewModel(@NonNull Application application) {
        super(application);
        wordRepository = new WordRepository(application);
    }

    public LiveData<List<Word>> getAllWordLive() {
        allWordLive = wordRepository.getAllWordLive();
        return allWordLive;
    }

    /********************使用下面那几个增删改查的接口,方便别人调用**************************/
    void insertWords(Word...words){
        wordRepository.insertWords(words);
    }

    void updateWords(Word...words){
        wordRepository.updateWords(words);
    }

    void deleteWords(Word...words){
        wordRepository.deleteWords(words);
    }

    void deleteAllWords(Void...voids){
        wordRepository.deleteAllWords();
    }

}
WordViewModel

MainActivyty

package com.example.roomtwo;

import androidx.appcompat.app.AppCompatActivity;
import androidx.lifecycle.LiveData;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProvider;
import androidx.lifecycle.ViewModelProviders;
import androidx.room.Room;

import android.os.AsyncTask;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;

import com.example.roomtwo.dao.Word;
import com.example.roomtwo.dao.WordDao;
import com.example.roomtwo.dao.WordDatabase;

import java.util.List;

public class MainActivity extends AppCompatActivity {

    WordDatabase wordDatabase;
    WordDao wordDao;
    WordViewModel wordViewModel;

    Button insertBtn;
    Button updateBtn;
    Button clearBtn;
    Button deleteBtn;
    TextView textView;

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

        //viewModel的实例化
        wordViewModel = ViewModelProviders.of(this).get(WordViewModel.class);

        //可被观察的数据
        wordViewModel.getAllWordLive().observe(this, new Observer<List<Word>>() {
            @Override
            public void onChanged(List<Word> words) {
                String text = null;
                for (int i = 0; i < words.size(); i++) {
                    Word word = words.get(i);
                    text += word.getId()+":"+word.getWord()+"="+word.getChineseMeaning();
                }
                textView.setText(text);
            }
        });

        //初始化各组件
        initBtnAndView();

        //插入
        insertBtn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Word word = new Word("hello", "你好");
                Word word1 = new Word("world", "世界");
                wordViewModel.insertWords(word,word1);
            }
        });

        //清空数据库表
        clearBtn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                wordViewModel.deleteAllWords();
            }
        });

        //删除某一个字段
        deleteBtn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Word word = new Word("", "");
                word.setId(270);
                wordViewModel.deleteWords(word);
            }
        });

        updateBtn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Word word = new Word("", "");
                word.setId(269);
                wordViewModel.updateWords(word);
            }
        });
    }

    void initBtnAndView(){
        insertBtn = findViewById(R.id.insertBtn);
        updateBtn = findViewById(R.id.updateBtn);
        clearBtn = findViewById(R.id.clearBtn);
        deleteBtn = findViewById(R.id.deleteBtn);
        textView = findViewById(R.id.textView);
    }

}
MainActivity

 

posted @ 2021-10-08 16:30  涂妖教  阅读(96)  评论(0)    收藏  举报