2016-10-25 16 views
0

SQLite.NetでSQLiteを使用していますが、すべての挿入にはほぼ15-20秒かかります。私は以下のような複雑な表を持っています。私のSQL接続がUWPでSqlite.Netを使用する際のパフォーマンスの問題

var platform = new SQLite.Net.Platform.WinRT.SQLitePlatformWinRT(); 
var connectionWithLock = new SQLiteConnectionWithLock(platform, _connectionParameters); 
var connection = new SQLiteAsyncConnection(() => connectionWithLock); 
SQLite.Net.Async.SQLiteAsyncConnection database = connection; 

され、挿入は

database.InsertWithChildrenAsync(assessmentQuestion,true).ConfigureAwait(false); 

のように見える私はので、私はパフォーマンスがとても悪いです方法を知りたいのSQLiteに新しいです

namespace Models 
{ 
    //SQLite Table AssessmentQuestions 
    [Table("AssessmentQuestions")] 
    public class AssessmentQuestion : INotifyPropertyChanged 
    { 
     //Autogenerate 
     private int _id; 
     [PrimaryKey, AutoIncrement] 
     [JsonIgnore] 
     public int Id 
     { 
      get 
      { 
       return _id; 
      } 
      set 
      { 
       this._id = value; 
       OnPropertyChanged(nameof(Id)); 
      } 
     } 
     private int _month; 
     public int Month 
     { 
      get 
      { 
       return _month; 
      } 
      set 
      { 
       this._month = value; 
       OnPropertyChanged(nameof(_month)); 
      } 
     } 

     //Some other ids as varibles here too 

     [OneToMany(CascadeOperations = CascadeOperation.All)] 
     public List<Facility> QuestionFacilityModel { get; set; } 

     public event PropertyChangedEventHandler PropertyChanged; 
     private void OnPropertyChanged(string propertyName) 
     { 
      this.PropertyChanged?.Invoke(this, 
       new PropertyChangedEventArgs(propertyName)); 
     } 
    } 

    //SQLite Table Facility 
    [Table("Facilities")] 
    public class Facility : INotifyPropertyChanged 
    { 
     //Autogenerate 
     private int _id; 
     [PrimaryKey, AutoIncrement] 
     [JsonIgnore] 
     public int Id 
     { 
      get 
      { 
       return _id; 
      } 
      set 
      { 
       this._id = value; 
       OnPropertyChanged(nameof(Id)); 
      } 
     } 

     private int _assessmentScheduleId; 
     public int AssessmentScheduleId 
     { 
      get 
      { 
       return _assessmentScheduleId; 
      } 
      set 
      { 
       this._assessmentScheduleId = value; 
       OnPropertyChanged(nameof(_assessmentScheduleId)); 
      } 
     } 

     //Some other ids as varibles here too 

     [ForeignKey(typeof(AssessmentQuestion))] 
     [JsonIgnore] 
     public int AssessmentQuestionId { get; set; } 

     [ManyToOne(CascadeOperations = CascadeOperation.All)] 
     [JsonIgnore] 
     public AssessmentQuestion AssessmentQuestion { get; set; } 

     [OneToMany(CascadeOperations = CascadeOperation.All)] 
     public ObservableCollection<SubFacility> SubFacility { get; set; } 

     public event PropertyChangedEventHandler PropertyChanged; 
     private void OnPropertyChanged(string propertyName) 
     { 
      this.PropertyChanged?.Invoke(this, 
       new PropertyChangedEventArgs(propertyName)); 
     } 
    } 

    //SQLite Table Sub Facility 
    [Table("SubFacilities")] 
    public class SubFacility : INotifyPropertyChanged 
    { 
     //Autogenerate 
     private int _id; 
     [PrimaryKey, AutoIncrement] 
     [JsonIgnore] 
     public int Id 
     { 
      get 
      { 
       return _id; 
      } 
      set 
      { 
       this._id = value; 
       OnPropertyChanged(nameof(Id)); 
      } 
     } 

     //Some other ids as varibles here too 

     [ForeignKey(typeof(Facility))] 
     [JsonIgnore] 
     public int FacilityId { get; set; } 

     [ManyToOne(CascadeOperations = CascadeOperation.All)] 
     [JsonIgnore] 
     public Facility Facility { get; set; } 

     [OneToMany(CascadeOperations = CascadeOperation.All)] 
     public List<Questions> Questions { get; set; } 

     public event PropertyChangedEventHandler PropertyChanged; 
     private void OnPropertyChanged(string propertyName) 
     { 
      this.PropertyChanged?.Invoke(this, 
       new PropertyChangedEventArgs(propertyName)); 
     } 
    } 

    //SQLite Table Questions 
    [Table("Questions")] 
    public class Questions : INotifyPropertyChanged 
    { 
     public Questions() 
     { 
      AssessmentImages = new string[0]; 
     } 

     //Autogenerate 
     private int _id; 
     [PrimaryKey, AutoIncrement] 
     [JsonIgnore] 
     public int Id 
     { 
      get 
      { 
       return _id; 
      } 
      set 
      { 
       this._id = value; 
       OnPropertyChanged(nameof(_id)); 
      } 
     } 
     private int _assessmentScheduleId; 
     public int AssessmentScheduleId 
     { 
      get 
      { 
       return _assessmentScheduleId; 
      } 
      set 
      { 
       this._assessmentScheduleId = value; 
       OnPropertyChanged(nameof(_assessmentScheduleId)); 
      } 
     } 
       //Some other ids as varibles here too 

     [SQLite.Net.Attributes.Ignore] 
     public virtual string[] AssessmentImages { get; set; } 

     private bool _imageExists; 
     public bool ImageExists 
     { 
      get 
      { 
       return _imageExists; 
      } 
      set 
      { 
       this._imageExists = value; 
       OnPropertyChanged(nameof(_imageExists)); 
      } 
     } 

     [ForeignKey(typeof(SubFacility))] 
     [JsonIgnore] 
     public int SubFacilityId { get; set; } 

     [ManyToOne(CascadeOperations = CascadeOperation.All)] 
     [JsonIgnore] 
     public SubFacility SubFacility { get; set; } 

     [OneToMany(CascadeOperations = CascadeOperation.All)] 
     public List<ControlTypes> ControlTypes { get; set; } 

     public event PropertyChangedEventHandler PropertyChanged; 
     private void OnPropertyChanged(string propertyName) 
     { 
      this.PropertyChanged?.Invoke(this, 
       new PropertyChangedEventArgs(propertyName)); 
     } 
    } 

    //SQLite Table ControlTypes 
    [Table("ControlTypess")] 
    public class ControlTypes 
    { 
     //Autogenerate 
     private int _id; 
     [PrimaryKey AutoIncrement] 
     [JsonIgnore] 
     public int Id 
     { 
      get 
      { 
       return _id; 
      } 
      set 
      { 
       this._id = value; 
       OnPropertyChanged(nameof(_id)); 
      } 
     } 
     private string _answerValue; 
     public string AnswerValue 
     { 
      get 
      { 
       return _answerValue; 
      } 
      set 
      { 
       this._answerValue = value; 
       OnPropertyChanged(nameof(_answerValue)); 
      } 
     } 
     private int _questionValueId; 
     public int QuestionValueId 
     { 
      get 
      { 
       return _questionValueId; 
      } 
      set 
      { 
       this._questionValueId = value; 
       OnPropertyChanged(nameof(_questionValueId)); 
      } 
     } 
     private string _questionValueName; 
     public string QuestionValueName 
     { 
      get 
      { 
       return _questionValueName; 
      } 
      set 
      { 
       this._questionValueName = value; 
       OnPropertyChanged(nameof(_questionValueName)); 
      } 
     } 
     private string _questionTypeId; 
     public string QuestionTypeId 
     { 
      get 
      { 
       return _questionTypeId; 
      } 
      set 
      { 
       this._questionTypeId = value; 
       OnPropertyChanged(nameof(_questionTypeId)); 
      } 
     } 
     private int _score; 
     public int Score 
     { 
      get 
      { 
       return _score; 
      } 
      set 
      { 
       this._score = value; 
       OnPropertyChanged(nameof(_score)); 
      } 
     } 
     private string _assessmentDetailId; 
     public string AssessmentDetailId 
     { 
      get 
      { 
       return _assessmentDetailId; 
      } 
      set 
      { 
       this._assessmentDetailId = value; 
       OnPropertyChanged(nameof(_assessmentDetailId)); 
      } 
     } 
     private string _assessmentAnswerId; 
     public string AssessmentAnswerId 
     { 
      get 
      { 
       return _assessmentAnswerId; 
      } 
      set 
      { 
       this._assessmentAnswerId = value; 
       OnPropertyChanged(nameof(_assessmentAnswerId)); 
      } 
     } 

     [ForeignKey(typeof(Questions))] 
     [JsonIgnore] 
     public int QuestionsId { get; set; } 

     [ManyToOne(CascadeOperations = CascadeOperation.All)] 
     [JsonIgnore] 
     public Questions Questions { get; set; } 

     public event PropertyChangedEventHandler PropertyChanged; 
     private void OnPropertyChanged(string propertyName) 
     { 
      this.PropertyChanged?.Invoke(this, 
       new PropertyChangedEventArgs(propertyName)); 
     } 
    } 

    public class StringOrArrayConverter : JsonConverter 
    { 
     public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) 
     { 
      switch (reader.TokenType) 
      { 
       case JsonToken.String: 
       case JsonToken.Null: 
        return reader.Value; 
       case JsonToken.StartArray: 
        reader.Read(); 
        if (reader.TokenType != JsonToken.EndArray) 
         throw new JsonReaderException("Empty array expected."); 
        return ""; 
      } 
      throw new JsonReaderException("Expected string or null or empty array."); 
     } 

     public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) 
     { 
      //var item = (string[])value; 
      //writer.WriteValue(item); 
      serializer.Serialize(writer, value); 
     } 

     public override bool CanConvert(Type objectType) 
     { 
      return objectType == typeof(string); 
     } 
    } 
} 

。私はSQLiteNetExtensionsAsync.Extensionsも使用しました。私は非同期呼び出しなしで使用しようとし、同じパフォーマンスを持っていた。ループの中でかなりの数の挿入を30〜40回行っているので、これには多くの時間がかかります。これをどのように改善できますか?

オブジェクトが複雑なので1つの挿入は複数のネストされた挿入を持つことができますが、平均で1つの挿入は異なる子オブジェクトの35-45個の挿入に相当します。そしてこの入れ子が問題を引き起こしているようです。

+0

プロファイラの下でコードを実行することにより、どのような情報を収集しましたか? – IInspectable

+0

これはDBにどのように行われたのか説明できますか? – AbsoluteSith

+0

[初級者向けパフォーマンスプロファイリング](https://msdn.microsoft.com/en-us/library/ms182372.aspx) – IInspectable

答えて

1

このメソッドをトランザクションで呼び出すと、処理が高速になります。これは、SQLiteの自身の勧告だ:http://www.sqlite.org/faq.html#q19

よろしく

+0

これは再帰的な挿入にどのように使用できますか?今、私は単純な挿入のサンプルしか見ることができません。そして、複雑なオブジェクトの一覧の[OneToMany(CascadeOperations = CascadeOperation.All)]という表に複雑なオブジェクトがあります。 – AbsoluteSith

+0

トランザクションを開始して、同じコードを実行してからトランザクションをコミットできませんか? –

+0

現在、私はInsertOrReplaceWithChildrenを実行するためにSQLiteNetExtensions.Extensionsを使用しています。ここで、4つのテーブルにまたがる複雑なオブジェクトを再帰的に挿入します。しかし、今私は文のSQLを介して行うのサンプルを見つけることができません。 – AbsoluteSith

関連する問題