sql >> データベース >  >> RDS >> SQLite

AndroidStudioのRoomデータベースを使用したテーブルの関連付け

    次の実例だと思います 目的を達成する方法の1つです。

    コード

    実験エンティティ(テーブル) Experiment.java

    @Entity
    public class Experiment {
    
        @PrimaryKey(autoGenerate = true)
        private long experimentId;
        private String experimentName;
        private String experimentDate;
    
        public Experiment() {
        }
    
        @Ignore
        public Experiment(String name, String date) {
            this.experimentName = name;
            this.experimentDate = date;
        }
    
        public long getExperimentId() {
            return experimentId;
        }
    
        public void setExperimentId(long experimentId) {
            this.experimentId = experimentId;
        }
    
        public String getExperimentName() {
            return experimentName;
        }
    
        public void setExperimentName(String experimentName) {
            this.experimentName = experimentName;
        }
    
        public String getExperimentDate() {
            return experimentDate;
        }
    
        public void setExperimentDate(String experimentDate) {
            this.experimentDate = experimentDate;
        }
    }
    
    • おそらく@Ignore以外に特別なことは何もありません 'dコンストラクター(便宜上)

    トライアルエンティティTrial.java

    @Entity
    public class Trial {
    
        @PrimaryKey(autoGenerate = true)
        private long trialId;
        @ForeignKey(entity = Experiment.class, parentColumns = {BaseColumns._ID},childColumns = "parentExperiment", onDelete = ForeignKey.CASCADE, onUpdate = ForeignKey.CASCADE)
        private long parentExperiment;
        private String trialVariable;
        private String trialResult;
    
        public Trial() {
        }
    
        @Ignore
        public Trial(long parentExperimentId, String variable, String result) {
            this.parentExperiment = parentExperimentId;
            this.trialVariable = variable;
            this.trialResult = result;
        }
    
        public long getTrialId() {
            return trialId;
        }
    
        public void setTrialId(long trialId) {
            this.trialId = trialId;
        }
    
        public long getParentExperiment() {
            return parentExperiment;
        }
    
        public void setParentExperiment(long parentExperiment) {
            this.parentExperiment = parentExperiment;
        }
    
        public String getTrialVariable() {
            return trialVariable;
        }
    
        public void setTrialVariable(String trialVariable) {
            this.trialVariable = trialVariable;
        }
    
        public String getTrialResult() {
            return trialResult;
        }
    
        public void setTrialResult(String trialResult) {
            this.trialResult = trialResult;
        }
    }
    
    • おそらく@Ignore以外に特別なことは何もありません 'dコンストラクター(便宜上)

    Dao.java(便宜上組み合わせて)

    public interface Dao {
    
        @Insert(onConflict = OnConflictStrategy.IGNORE)
        long[] insertExperiments(Experiment... experiments);
    
        @Insert(onConflict = OnConflictStrategy.IGNORE)
        long insertExperiment(Experiment experiment);
    
        @Insert(onConflict = OnConflictStrategy.IGNORE)
        long[] insertTrials(Trial... trials);
    
        @Insert(onConflict = OnConflictStrategy.IGNORE)
        long insertTrial(Trial trial);
    
        @Update(onConflict = OnConflictStrategy.IGNORE)
        int updateExperiments(Experiment... experiments);
    
        @Update(onConflict = OnConflictStrategy.IGNORE)
        int updateExperiment(Experiment experiment);
    
        @Update(onConflict = OnConflictStrategy.IGNORE)
        int updateTrials(Trial... trials);
    
        @Update(onConflict = OnConflictStrategy.IGNORE)
        int updateTrial(Trial trial);
    
        @Delete
        int deleteExperiments(Experiment... experiments);
    
        @Delete
        int deleteExperiment(Experiment experiment);
    
        @Delete
        int deleteTrials(Trial... trials);
    
        @Delete
        int deleteTrial(Trial trial);
    
        @Query("SELECT * FROM Experiment")
        List<Experiment> getAllexperiments();
    
        @Query("SELECT * FROM Experiment WHERE experimentDate BETWEEN :startdate AND :enddate")
        List<Experiment> getExperimentsInDateRange(String startdate, String enddate);
    
        @Query("SELECT * FROM Trial")
        List<Trial> getAllTrials();
    
        @Query("SELECT * FROM Experiment JOIN Trial ON parentExperiment = experimentId")
        List<TrialWithExperiment> getExperimentsWithTrials();
    
    
        public class TrialWithExperiment {
            private long experimentId;
            private String experimentName;
            private String experimentDate;
            private long trialId;
            private String trialVariable;
            private String trialResult;
    
            public long getExperimentId() {
                return experimentId;
            }
    
            public void setExperimentId(long experimentId) {
                this.experimentId = experimentId;
            }
    
            public String getExperimentName() {
                return experimentName;
            }
    
            public void setExperimentName(String experimentName) {
                this.experimentName = experimentName;
            }
    
            public String getExperimentDate() {
                return experimentDate;
            }
    
            public void setExperimentDate(String experimentDate) {
                this.experimentDate = experimentDate;
            }
    
            public void setTrialId(long trialId) {
                this.trialId = trialId;
            }
    
            public long getTrialId() {
                return trialId;
            }
    
            public String getTrialVariable() {
                return trialVariable;
            }
    
            public void setTrialVariable(String trialVariable) {
                this.trialVariable = trialVariable;
            }
    
            public String getTrialResult() {
                return trialResult;
            }
    
            public void setTrialResult(String trialResult) {
                this.trialResult = trialResult;
            }
        }
    }
    
    • TrialWithExperimentに注意してください クラス、これはトライアルとそれが所有するエクスペリメントの組み合わせを定義します。
    • 列名がどのように区別されるかに注意してください。 IDだけでなくexperimentId およびtrialId それらを区別します。
    • 最後の@Queryに注意してくださいgetExperimentsWithTrials() これにより、実験のリストが返されます。

    @ Database ExperimentDatabase.java

    @Database(entities = {Experiment.class, Trial.class}, version = 1,exportSchema = false)
    public abstract class ExperimentDatabase extends RoomDatabase {
        public abstract Dao getDao();
    } 
    

    最後に、上記を利用したアクティビティ:-

    public class MainActivity extends AppCompatActivity {
    
        ExperimentDatabase mDB;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
    
            mDB = Room.databaseBuilder(this,ExperimentDatabase.class,"experimentdb").allowMainThreadQueries().build();
            mDB.getDao().insertExperiments(new Experiment[]{
                    new Experiment("Experiment 1","2019-01-01"),
                    new Experiment("Experiment 2", "2019-02-01")
            });
            List<Experiment> experiments = mDB.getDao().getExperimentsInDateRange("2019-01-01","2019-12-31");
            for (Experiment e: experiments) {
                Log.d("EXPERIMENTS", "Experiment is " + e.getExperimentName() + " on " + e.getExperimentDate());
            }
    
            experiments = mDB.getDao().getAllexperiments();
            for (Experiment e: experiments) {
                Log.d("EXPERIMENTS", "Experiment is " + e.getExperimentName() + " on " + e.getExperimentDate());
            }
    
            for (Experiment e: experiments) {
                mDB.getDao().insertTrial(
                        new Trial(
                                e.getExperimentId(),
                                "Variable for " + e.getExperimentName(),
                                "Result for Experiment on " + e.getExperimentDate()
                        )
                );
            }
    
            List<Trial> trials = mDB.getDao().getAllTrials();
            for (Trial t: trials ) {
                Log.d("TRIAL ",
                        "Trial is for ExperimentID " + String.valueOf(t.getParentExperiment()) +
                                "\n\tVariable = " + t.getTrialVariable() +
                                "Result = " + t.getTrialResult()
                );
            }
    
    
            List<Dao.TrialWithExperiment> trialsWithExperiments = mDB.getDao().getExperimentsWithTrials();
    
            for (Dao.TrialWithExperiment te:trialsWithExperiments) {
                Log.d(
                        "TRIALWITHEXPERIMENT",
                        "Experiment Name = " + te.getExperimentName() +
                                "\n\tExperiment Date = " + te.getExperimentDate() +
                                "\n\t\tTrial Variable = " + te.getTrialVariable() +
                                "\n\t\tTrial Result = " + te.getTrialResult()
                );
    
            }
        }
    }
    

    これ:-

    • 2つの実験を追加します(実行ごと)
    • 日付範囲で実験を取得し(これはSQLiteで認識される日付形式を想定しています)、ログに出力します。
    • すべての実験を取得してログに出力します。
    • 実験のリストを使用して、各実験に試行を追加します。
    • すべての試行を取得してログに出力します。
    • 親の実験とともにすべての試行を取得し、ログに出力します。

    結果

    05-28 10:19:42.770 5750-5750/? D/EXPERIMENTS: Experiment is Experiment 1 on 2019-01-01
    05-28 10:19:42.770 5750-5750/? D/EXPERIMENTS: Experiment is Experiment 2 on 2019-02-01
    05-28 10:19:42.776 5750-5750/? D/EXPERIMENTS: Experiment is Experiment 1 on 2019-01-01
    05-28 10:19:42.776 5750-5750/? D/EXPERIMENTS: Experiment is Experiment 2 on 2019-02-01
    05-28 10:19:42.786 5750-5750/? D/TRIAL: Trial is for ExperimentID 1
          Variable = Variable for Experiment 1Result = Result for Experiment on 2019-01-01
    05-28 10:19:42.786 5750-5750/? D/TRIAL: Trial is for ExperimentID 2
          Variable = Variable for Experiment 2Result = Result for Experiment on 2019-02-01
    05-28 10:19:42.787 5750-5750/? D/TRIALWITHEXPERIMENT: Experiment Name = Experiment 1
          Experiment Date = 2019-01-01
              Trial Variable = Variable for Experiment 1
              Trial Result = Result for Experiment on 2019-01-01
    05-28 10:19:42.787 5750-5750/? D/TRIALWITHEXPERIMENT: Experiment Name = Experiment 2
          Experiment Date = 2019-02-01
              Trial Variable = Variable for Experiment 2
              Trial Result = Result for Experiment on 2019-02-01
    

    代替/追加

    別のアプローチは、 @Relationを利用することです。 実験ごとに、そのオブジェクト内の関連/関連するトライアルのリストを含むオブジェクトを作成します。

    上記を拡張すると、以下を Dao.javaに追加できます。

    @Query("SELECT * FROM  Experiment")
    List<ExperimentWithTrials> getExperimentsAndTrials();
    
    class ExperimentWithTrials {
        private long experimentId;
        private String experimentName;
        private String experimentDate;
        @Relation(parentColumn = "experimentId", entityColumn = "parentExperiment")
        List<Trial> trials;
    
        public long getExperimentId() {
            return experimentId;
        }
    
        public void setExperimentId(long experimentId) {
            this.experimentId = experimentId;
        }
    
        public String getExperimentName() {
            return experimentName;
        }
    
        public void setExperimentName(String experimentName) {
            this.experimentName = experimentName;
        }
    
        public String getExperimentDate() {
            return experimentDate;
        }
    
        public void setExperimentDate(String experimentDate) {
            this.experimentDate = experimentDate;
        }
    
        public List<Trial> getTrials() {
            return trials;
        }
    
        public void setTrials(List<Trial> trials) {
            this.trials = trials;
        }
    }
    

    次に、以下を MainActivity.javaに追加できます。

        List<Dao.ExperimentWithTrials> experimentsWithTrials = mDB.getDao().getExperimentsAndTrials();
        for (Dao.ExperimentWithTrials et: experimentsWithTrials ) {
            Log.d(
                    "EXPERIMENTANDTRIALS",
                    "Experiment Name = " + et.getExperimentName() +
                            "\n\tExperiment Date = " + et.getExperimentDate()
            );
            for (Trial t: et.getTrials()) {
                Log.d(
                        "TRIALFOREXPERIMENT",
                        "\t\tVariable = " + t.getTrialVariable() +
                                "\n\t\tResult = " + t.getTrialResult()
                );
            }
        }
    }
    
    • ExperimentWithTrialsが埋め込まれたトライアルのリストをループすることでトライアルがどのように取得されるかに注意してください。 以前の実験データと試行データを組み合わせたリストとは対照的に、オブジェクト。

      • これはおそらくOOの方法をより純粋にするためです。
      • ただし、SQLiteに関しては、複数のクエリを実行しているように見えるため、これは面倒で非効率的であるように見えます。 1つは実験を取得し、もう1つは各実験の基礎となる試行を取得します。

    結果の追加出力

    05-28 13:05:35.052 6524-6524/? D/EXPERIMENTANDTRIALS: Experiment Name = Experiment 1
          Experiment Date = 2019-01-01
    05-28 13:05:35.052 6524-6524/? D/TRIALFOREXPERIMENT:      Variable = Variable for Experiment 1
              Result = Result for Experiment on 2019-01-01
    05-28 13:05:35.052 6524-6524/? D/EXPERIMENTANDTRIALS: Experiment Name = Experiment 2
          Experiment Date = 2019-02-01
    05-28 13:05:35.052 6524-6524/? D/TRIALFOREXPERIMENT:      Variable = Variable for Experiment 2
              Result = Result for Experiment on 2019-02-01
    
    • 便宜上、上記のすべてがメインスレッドで実行されていることに注意してください(つまり、 .allowMainThreadQueries() 使用されています)。推奨事項に従う場合、すべてのデータベースアクセスは別のスレッドを介して行われます。その場合、クエリには@Transactionアノテーションが推奨されます。



    1. Atomic UPDATE..PostgresのSELECT

    2. SQL Serverジョブは、既に実行されている場合、スケジュールされた実行をスキップしますか?

    3. Djangoの新しいPostgres機能を楽しんでください

    4. SQLServerでサブクエリを使用する方法に関する簡単なガイド