Как сохранить объекты в файл в Android Kotlin

#android #kotlin

#Android #kotlin

Вопрос:

У меня есть файл RecordDAO.kt, который дал мне мой профессор, и мы должны отредактировать его, чтобы программа работала так, как должна. Сама программа является своего рода регистратором успеваемости учащихся, где я могу добавлять новые выступления учащихся, чтобы показывать их в виде списка.

RecordDAO выглядит следующим образом:

 class RecordDAO(private val ctx: Context) {
    private var nextId = 0
    private val records = initRecords()

    fun findAll(): List<Record> = records.toList()

    fun findById(id: Int): Record? {
        var record: Record? = Record()
        records.forEach { if(it.id == id) record = it }
        return record
    }
    /**
     * Ersetzt das übergebene [Record] Objekt mit einem bereits gespeicherten [Record] Objekt mit gleicher id.
     *
     * @param record
     * @return true = update ok, false = kein [Record] Objekt mit gleicher id im Speicher gefunden
     */
    fun update(record: Record): Boolean {
        var existing = false
        records.forEach {
            if(it.id == record.id){
                val index= records.indexOf(it)
                records[index] = record
                existing = true
            }
        }
        return existing
    }

    /**
     * Persistiert das übergebene [Record] Objekt und liefert die neue id zurück.
     * (Seiteneffekte: record.id = nextId; nextId  = 1 )
     *
     * @param record
     * @return neue record id
     */
    fun persist(record: Record): Int {
        saveRecords()
        record.id = nextId
        records.add(record)
        return record.id!!
    }

    /**
     * Löscht das übergebene [Record] Objekt anhand der id aus dem Speicher.
     *
     * @param record
     * @return true = ok, false = kein [Record] Objekt mit gleicher id im Speicher gefunden
     */
    fun delete(record: Record): Boolean {
        var existing = false
        records.forEach {
            if(it.id == record.id){
                val index:Int = records.indexOf(it)
                records.removeAt(index)
                existing = true
            }
        }
        return existing
    }

    private fun initRecords(): MutableList<Record> {
        val records = mutableListOf<Record>()
        val f = ctx.getFileStreamPath(FILE_NAME)
        if (f.exists()) {
            ctx.openFileInput(FILE_NAME).use { fin ->
                ObjectInputStream(fin).readObject().let { obj ->
                    records.addAll(obj as MutableList<Record>)
                    // init next id
                    if (records.size > 0) {
                        nextId  = 1
                    }
                }

            }
        }
        return records;
    }

    private fun saveRecords() {
        ctx.openFileOutput(FILE_NAME, Context.MODE_PRIVATE)
                .use { ObjectOutputStream(it).writeObject(records) }
    }

    companion object {
        private const val FILE_NAME = "records.obj"
    }
}
 

У меня есть несколько вопросов к этому коду, что именно делает функция saveRecords, создает ли она файл и сохраняет в нем список или я должен создать этот файл вручную.

Мой файл формы формы Kotlin выглядит следующим образом:

 class RecordFormActivity : AppCompatActivity() {

    private var record = Record()

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_record_form)

        val names = resources.getStringArray(R.array.module_names)

        val adapter = ArrayAdapter(this, simple_dropdown_item_1line, names)
        moduleName.setAdapter(adapter)
    }

    fun onSave(view: View) {
        var isValid = true

        record.moduleNum = moduleNum.text.toString().trim().ifEmpty {
            moduleNum.error = getString(R.string.module_num_not_empty)
            isValid = false
            ""
        }

        record.moduleName = moduleName.text.toString().ifEmpty {
            moduleName.error = getString(R.string.module_name_not_empty)
            isValid = false
            ""
        }

        if(isValid){
            if(record.id == null) RecordDAO(this).persist(record)
            else(RecordDAO(this).update(record))
        }

        finish()

    }
}
 

Где я должен вызвать метод saveRecords, чтобы данные сохранялись в файл и извлекались после закрытия и повторного открытия приложения?

Должен ли я также публиковать свои XML-файлы макета?

Ответ №1:

В соответствии с этим источником метод writeObject используется для записи объекта в поток. Таким образом, вам не нужно редактировать функцию saveRecords.

В классе RecordFormActivity вы можете вызвать saveRecords либо в функции OnSave, либо в функции переопределения onDestroy . если у вас есть кнопка сохранения, я советую вам вызвать saveRecords в вашей функции OnSave, в противном случае вы можете вызвать ее в onDestroy.

Комментарии:

1. Метод initRecords не считывает дату из файла?

2. вы правы, я, должно быть, что-то упустил из виду. Метод initRecords считывает и возвращает изменяемый список сохраненных записей. но все же вам нужно установить значения, возвращаемые из initRecords, в ваши представления о функции oncreate.

3. Хорошо, я это сделал, но как мне вызвать метод saveRecords в другой функции, он является закрытым

4. вы можете вызвать функцию сохранения, она является общедоступной и используется только там, где используется функция saveRecords.

5. Я написал это там, но это не работает, должен ли я записать это в конце функции сохранения?