【问题标题】:SqLiteDatabase writable Vs. ReadOnlySqlLiteDatabase 可写 Vs。只读
【发布时间】:2017-10-29 18:05:06
【问题描述】:

我不明白他们为什么要在逻辑或中编写两个相反的变量。 正确 ||假=真,或假||真 = 真。为什么这个检查是必要的?

if (mDatabase != null) {
            if (!mDatabase.isOpen()) {
                // Darn!  The user closed the database by calling mDatabase.close().
                mDatabase = null;
            } else if (!writable || !mDatabase.isReadOnly()) {
                // The database is already open for business.
                return mDatabase;
            }
        }

注意: 同样的逻辑也适用于 Samba 文件共享。 有一个 Samba 解释http://www.linuxtopia.org/online_books/network_administration_guides/using_samba_book/ch04_05_06.html

谁能在这里澄清一下?

我上面介绍的代码存根在 SQLiteOpenHelper 类中,从第 222 行到第 231 行

https://android.googlesource.com/platform/frameworks/base/+/refs/heads/master/core/java/android/database/sqlite/SQLiteOpenHelper.java

【问题讨论】:

    标签: java android samba sqliteopenhelper


    【解决方案1】:

    可写定义为:

    1. 如果磁盘是 R-W
    2. 如果写数据库的进程有写权限。

    注意:这里可写与你的理解无关。

    对于 ReadOnly,有一个逻辑,因为 ReadOnly 不是 Writable 的对立面。这就是你感到困惑的地方。

    ReadOnly 中包含三个内容:OPEN_READONLY、OPEN_READ_MASK 和 OpenFlags。

    注意: OPEN_READONLY 与 Writable 完全相反。这是你不清楚的地方。

    解释 OPEN_READ_MASK -- 我们将其设置为 1(即十六进制的 0X00000001) OPEN_READONLY -- 我们将其设置为 1(即十六进制的 0X00000001)

    OpenFlags - 有时为 1,有时为 0。如果磁盘未满则为 1。如果磁盘已满,则为 0。

    而且,我们计算 ReadOnly = (OpenFlags & OPEN_READ_MASK == OPEN_READONLY)。现在,从这个 & 操作中,ReadOnly 总是确保即使数据库是 OPEN_READONLY,它仍然需要满足它没有满。如果它已满,则 ReadOnly 变为 false。

    这就是为什么对于每个文件和数据库,上面实现的 & 操作都是可靠的。

    证明:

    如果你 ctrl+Alt 点击 isReadOnly() 的方法,你会看到下面的代码行。

    public boolean isReadOnly() {
            synchronized (mLock) {
                return isReadOnlyLocked();
            }
        }
    

    你进一步Ctrl+Alt+点击方法isReadOnlyLocked(),你会看到下面的代码行。

    private boolean isReadOnlyLocked() {
            return (mConfigurationLocked.openFlags & OPEN_READ_MASK) == OPEN_READONLY;
        }
    

    您可以通过进一步的 Ctrl+Alt+click 看到 OPEN_READ_MASK 和 OPEN_READONLY 是如何定义的,您会看到下面的代码行。

    /**
         * Open flag: Flag for {@link #openDatabase} to open the database for reading only.
         * This is the only reliable way to open a database if the disk may be full.
         */
        public static final int OPEN_READONLY = 0x00000001;           // update native code if changing
    
        private static final int OPEN_READ_MASK = 0x00000001;         // update native code if changing
    

    如果磁盘已满,系统会将 openFlags 更改为 0,以确保即使磁盘是 Openly readOnly 仍然因为没有磁盘空间而无法写入。现在,我相信你已经清楚了。

    【讨论】:

      【解决方案2】:

      您误解了writable 参数。它不指示当前数据库或连接的状态。它表明用户是否想要一个他们可以写入的数据库连接,或者只读连接是否足够。

      这一行说——如果用户不想要一个可写的连接,如果数据库允许用户写,那么当前数据库就可以了。换句话说,如果用户特别请求了一个可写的数据库,但当前的连接是只读的,我们就会越过这一行(并做更多的连接工作)。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2020-03-01
        • 2016-09-26
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多