何时调用SQLiteOpenHelper onCreate方法?

何时调用SQLiteOpenHelper onCreate方法?,sqlite,android-sqlite,Sqlite,Android Sqlite,我试图创建一个SQLite数据库并用它做一些事情。但是我发现我的onCreate方法甚至没有被调用 在onCreate方法开始时,我正在向LogCat发送一条消息 我的假设是,(超级)构造函数将调用onCreate方法。是这样吗 我的代码: import android.database.sqlite.SQLiteOpenHelper; import android.database.sqlite.SQLiteDatabase; import android.content.Context; i

我试图创建一个SQLite数据库并用它做一些事情。但是我发现我的
onCreate
方法甚至没有被调用

onCreate
方法开始时,我正在向LogCat发送一条消息

我的假设是,(超级)构造函数将调用onCreate方法。是这样吗

我的代码:

import android.database.sqlite.SQLiteOpenHelper;
import android.database.sqlite.SQLiteDatabase;
import android.content.Context;
import android.database.Cursor;
import android.content.ContentValues;
import android.util.Log;

public class DatabaseHandler extends SQLiteOpenHelper {
    // Static Constants
    /*** Database details ***/
    // Database version
    private static final int DATABASE_VERSION           = 1;

    // Database name
    private static final String DATABASE_NAME           = "database_name";

    /*** Database Tables ***/
    /** Events **/
    // Event table
    private static final String TABLE_EVENT             = "event";

    // Event table columns
    private static final String COLUMN_EVENT_EID        = "_eid";

    private static final String COLUMN_EVENT_CREATION_DATE  = "creation_date";

    private static final String COLUMN_EVENT_TITLE      = "title";
    private static final String COLUMN_EVENT_ICON       = "icon";

    public DatabaseHandler(Context context) {
        super(context, DATABASE_NAME, null, DATABASE_VERSION);
    }

    @Override
    public void onCreate(SQLiteDatabase db) {
        Log.e("MyApp", "onCreate invoked");
        // Tables creation queries
        String CREATE_EVENT_TABLE = "create table " + TABLE_EVENT + "(" + COLUMN_EVENT_EID + " integer primary key, "
                + COLUMN_EVENT_CREATION_DATE + " text, "
                + COLUMN_EVENT_TITLE + " text, "
                + COLUMN_EVENT_ICON + " text)";

        // Creating tables
        db.execSQL(CREATE_EVENT_TABLE);
    }

    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
        Log.e("MyApp", "onUpgrade invoked");
        db.execSQL("DROP TABLE IF EXISTS " + TABLE_EVENT);
    }
}
main活动代码:

import android.os.Bundle;
import android.app.Activity;
import android.view.Menu;

public class MainActivity extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        DatabaseHandler db = new DatabaseHandler(this);
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.main, menu);
        return true;
    }

}
报告说:

在调用或之前,不会实际创建或打开数据库

如果您是对的,(超级)构造函数将调用onCreate方法,但只有在实际数据库不存在时才调用。 从

用于管理数据库创建和版本管理的帮助器类

创建一个子类,实现onCreate(SQLiteDatabase), onUpgrade(SQLiteDatabase,int,int)和可选 onOpen(SQLiteDatabase),该类负责打开 数据库(如果存在),创建数据库(如果不存在),并将其升级为 必要的


正如官方文件所说,“getWritableDatabase()创建和/或打开一个用于读写的数据库。第一次调用时,将打开数据库并调用onCreate(SQLiteDatabase)、onUpgrade(SQLiteDatabase、int、int)和/或onOpen(SQLiteDatabase)。”

一旦成功打开,数据库将被缓存,因此您可以在每次需要写入数据库时调用此方法。(请确保在不再需要数据库时调用close())错误(如权限错误或磁盘已满)可能会导致此方法失败,但如果问题得到解决,则以后的尝试可能会成功


让我清除逻辑流程上的问题。这里是延迟初始化的概念

DatabaseHandler
上的(超级)构造函数将不会调用onCreate方法。调用DatabaseHandler构造函数将初始化:上下文、数据库名称、创建数据库的工厂、数据库版本和数据库错误处理程序

getWritableDatabase()getDatabaseLocked()>-SQLiteDatabase.create()

getReadableDatabase()getDatabaseLocked()>-SQLiteDatabase.create()

回答:成功创建数据库后,您的配置会发生更改,下次再次
getReadableDatabase()
getwriteabledatabase()
调用
getDatabaseLocked()
并执行
onCreate(db)
中的方法
getDatabaseLocked()

说明:

import android.os.Bundle;
import android.app.Activity;
import android.view.Menu;

public class MainActivity extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        DatabaseHandler db = new DatabaseHandler(this);
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.main, menu);
        return true;
    }

}
上面的
SQLiteDatabase.create()
方法负责在磁盘中创建SQLiteDatabase

但是延迟初始化的过程(也就是说,它没有准备好所有的东西。如果需要,它会在运行时创建这些对象。为此,它使用了大量的
if..else
语句)

如果您看到
getDatabaseLocked()
的全文,如下所示。[您可以在
getDatabaseLocked()
的主体中搜索
onCreate()
方法]

请注意,在
getDatabaseLocked()
方法的主体中,有很多if。。其他情况。如果。。else案例确定您当前的环境(配置),并根据您当前的环境调用适当的方法来初始化/配置所需的任何内容

另外,请注意:
DatabaseHandler
(实现了
SQLiteOpenHelper
的类)中的所有回调方法都在
getDatabaseLocked()
主体内调用

源代码
SQLiteOpenHelper.java

源代码
SQLiteDatabase.java

样本如下: