【问题标题】:Prevent data duplication in the SQLite Database防止 SQLite 数据库中的数据重复
【发布时间】:2016-04-18 16:42:50
【问题描述】:

我正在开发一个使用 SQLite 作为本地数据库的 android 应用程序。该应用程序同步从 Web api 获得的数据并将其存储在本地数据库中。所有模型类的 ID 属性都设置为主键并自动递增,因此我可以手动输入数据而无需指定 ID。问题是当我将 API 中的数据插入 SQlite 时,对象的 ID 被忽略,Sqlite 为对象提供了一个新的 ID。我希望存储的数据与正在存储的对象具有相同的 ID。

Web API 返回 ID 类型为 long 但 SQLite 对象的主键为 int 的对象列表。这是因为 ID 值的数据类型不匹配而没有被存储的原因吗?我无法更改数据来源的 SQL 数据库中的数据类型,因为其中有数百个表。有办法解决吗?

这是在我的本地数据库中插入或更新数据的代码:

    }
    public async Task<string> insertUpdateVideoData(Video_Struct data)
    {
        try
        {
            var db = new SQLiteAsyncConnection(dbPath);
            var m = GetVideos();
            if (await db.FindAsync<Video_Struct>(f => f.VideoID == data.VideoID) != null)
            {

                await db.UpdateAsync(data);
            }
            else
            {
                if (await db.InsertAsync(data) != 0)
                {

                    await db.UpdateAsync(data);
                }

            }
            return "Single data file inserted or updated";
        }
        catch (SQLiteException ex)
        {
            return ex.Message;
        }
    }

这是从 API 获取数据对象的代码:

    public async Task<List<Video_Struct>> GetVideoData()
    {
        List<Video_Struct> vids = new List<Video_Struct>();
        WebClient mClient = new WebClient();
        var output = await mClient.DownloadDataTaskAsync(new Uri(GlobalVariables.host + "/api/media/getmedia"));
        var json = Encoding.UTF8.GetString(output);
        vids = JsonConvert.DeserializeObject<List<Video_Struct>>(json);
        return vids;
    }

【问题讨论】:

  • 基于this answer,SQLite 数据类型是每个值,而不是每个列,所以你写的任何类型都应该是你得到的。
  • 如果 ID 值匹配,那么为什么插入的数据得到的值与我从 API 对象得到的值不同?
  • 向我们展示您读写的代码。
  • @TimBiegeleisen 我已经用代码更新了我的 OP
  • 定义数据模型中的重复项。

标签: android mysql database sqlite


【解决方案1】:

如果您的本地数据库是 Web 数据的缓存,而外部数据库为您提供唯一 ID,请不要在方案中使用自动增量,只需重复使用外部 ID。

实际上,您可以拥有一个复杂的(复合)主键,这取决于数据的唯一属性。

如果您不将数据作为结构化集处理,您可以尝试gson+SharedPreferences。只是不要忘记为您的数据模型覆盖 equals 和 hashcode。

数据类型不是问题,因为 sqlite 使用 INTEGER type

【讨论】:

  • 我可以这样做,但它会阻止我在不指定 ID 的情况下手动在本地数据库中输入数据。
  • 手动输入数据有什么用?如果是用于测试,您可以查询最高 id,然后在插入之前将其递增。
  • 就像我必须从应用程序中插入数据对象一样,我可以指定除 ID 之外的所有其他属性的值。是的,这可能是一种解决方案
猜你喜欢
  • 2018-12-29
  • 2016-07-23
  • 1970-01-01
  • 2022-08-19
  • 1970-01-01
  • 2012-01-21
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多