首页 文章

使用Arraylist填充房间数据库

提问于
浏览
0

我想构建一个Deckbuilder,它允许您在设备上本地保存创建的套牌 .

Decklist存储在Arraylists中,名为 TransferDeck . 我想在房间数据库中存储 . My issue is, that I do not know how to populate my database correctly, with the data comming out of the Arraylist.

我习惯和Arraylist一起工作,下面你看看我存储数据的尝试:

So this is what I tried but what sadly does not work:

private void populateDB(final List<TransferDeck> mTransferDeck) {
            new Thread(new Runnable() {
                @Override
                public void run() {
                    List<SaveDeck> mSaveDeck = new ArrayList<>();
                    for(int i = 0; i<mTransferDeck.size(); i++){
                        mSaveDeck.add(new SaveDeck(i, "FirstSavedDeck", mTransferDeck.get(i).getCardImage() ,mTransferDeck.get(i).getTypeImage(), mTransferDeck.get(i).getCost(), mTransferDeck.get(i).getName(), mTransferDeck.get(i).getNumber()));
                    }
                    mSavedDecksDB.deckBuilderDao().insertCards(mSaveDeck);

                }
            }).start();
}

Below you can find the rest of my code, but the above one should be enough to make clear what I want to do...

  • 我创建了SaveDeck类,它应该能够使用给定的Deckname保存甲板: -

@Entity公共类SaveDeck实现Serializable {@PrimaryKey(autoGenerate = true)private int _id;

public SaveDeck(int _id, String deckName, int cardImage, int typeImage, Integer cardCost, String cardName, Integer cardNumber) {
    this._id = _id;
    DeckName = deckName;
    CardImage = cardImage;
    TypeImage = typeImage;
    CardCost = cardCost;
    CardName = cardName;
    CardNumber = cardNumber;
}

@ColumnInfo(name = "DeckName")
private String DeckName;

@ColumnInfo(name = "CardImage")
private int CardImage;

@ColumnInfo(name = "TypeImage")
private int TypeImage;

@ColumnInfo(name = "CardCost")
private Integer CardCost;

@ColumnInfo(name = "CardName")
private String CardName;

@ColumnInfo(name = "CardNumber")
private Integer CardNumber;

}

  • 我按如下方式创建了Dao类:: -

@Dao公共接口DeckBuilderDao {

@Insert(onConflict = OnConflictStrategy.IGNORE)
public long[] insertCards(SaveDeck... saveDecks);

@Insert(onConflict = OnConflictStrategy.IGNORE)
public long insertCard(SaveDeck saveDecks);

@Update
public int updateCardBaseEntries(SaveDeck... saveDecks);

@Update
public int updateCardBaseEntry(SaveDeck saveDecks);

@Delete
public int deleteCardBaseEntried(SaveDeck... saveDecks);

@Delete
public int deleteCardBaseEntry(SaveDeck saveDecks);

@Query("SELECT * FROM SaveDeck")
public SaveDeck[] getAllDecks();

//probably I do not need the getAllDecks Query. Right now I only need the following one:
@Query("SELECT * FROM SaveDeck WHERE DeckName = :NameOfDeck ORDER  BY DeckName, CardName")
public SaveDeck getOneDeck(String NameOfDeck);

}

  • 此外创建了DataBase类:
@Database(entities = {SaveDeck.class}, version = 1)
public abstract class SaveDecksDataBase extends RoomDatabase {
    public abstract DeckBuilderDao deckBuilderDao();
}
  • 最后一个类是一个片段,我尝试填充我的数据库,而 populateDB() 类是问题

public class review_fragment extends Fragment {

private List<TransferDeck> mTransferDeck = DataHolder.getInstance().savedDecklistTransfer;
SaveDecksDataBase mSavedDecksDB;
Cursor mCursor;

public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
//return super.onCreateView(inflater, container, savedInstanceState);
    View view = inflater.inflate(R.layout.review_fragment, container, false);

    /*Introduce Cards Recycler*/

    RecyclerView rvCards = view.findViewById(R.id.rv_review_cardlist);
    rvCards.setLayoutManager(new GridLayoutManager(getActivity(), 5));
    review_RViewAdapter_Cards adapterCards = new review_RViewAdapter_Cards(getContext(), mTransferDeck);
    rvCards.setAdapter(adapterCards);



    /*Init Room database*/
    mSavedDecksDB = Room.databaseBuilder(getActivity(),SaveDecksDataBase.class,"SavedDecksDB.db").build();
    populateDB(mTransferDeck);

    return view;
}

private void populateDB(final List<TransferDeck> mTransferDeck) {
    new Thread(new Runnable() {
        @Override
        public void run() {
            List<SaveDeck> mSaveDeck = new ArrayList<>();
            for(int i = 0; i<mTransferDeck.size(); i++){
                mSaveDeck.add(new SaveDeck(i, "FirstSavedDeck", mTransferDeck.get(i).getCardImage() ,mTransferDeck.get(i).getTypeImage(), mTransferDeck.get(i).getCost(), mTransferDeck.get(i).getName(), mTransferDeck.get(i).getNumber()));
            }
            mSavedDecksDB.deckBuilderDao().insertCards(mSaveDeck);

        }
    }).start();
}

}

1 回答

  • 0

    我想提一下,这应该是一个评论而不是一个答案 .

    首先,使用AysncTask或使用更强大的 Executors.newSingleThreadExecutor() . 如果您更喜欢第二个,那么最好是创建一个帮助类(example) . 例:

    private void populateDB(final List<TransferDeck> mTransferDeck) {
        AppExecutors.diskIO().execute(() -> {
    
            for(int i = 0; i<mTransferDeck.size(); i++){
                mSavedDecksDB.deckBuilderDao().insertCards(new SaveDeck(...);
            }
    
        });
    }
    

    (1)创建一个空白构造函数 .

    (4)房间数据库不应该在那里初始化,如果它是单身的话最好 . 所以你的数据库类(3)可以是这样的:

    public abstract class SaveDecksDataBase extends RoomDatabase {
    
       private static SaveDecksDataBase sINSTANCE;
       private static final Object LOCK = new Object();
    
       public static SaveDecksDataBase getDatabase(final Context context) {
            if (sINSTANCE == null) {
                synchronized (LOCK) {
                    if (sINSTANCE == null) {
                        sINSTANCE = Room.databaseBuilder(context.getApplicationContext(),
                                SaveDecksDataBase.class, "SavedDecksDB.db")
                                .build();
                    }
                }
            }
            return sINSTANCE;
        }
    
        public abstract DeckBuilderDao deckBuilderDao();
    }
    

    最后,要获取 SaveDeck 对象,您还必须使用 ExecutorsAsyncTask 在后台进行工作,然后填充 RecyclerView .

相关问题