【问题标题】:SQLite Dynamic where-clause for ToggleButtons用于切换按钮的 SQLite 动态 where 子句
【发布时间】:2018-10-22 01:23:06
【问题描述】:

我想创建一个动态 where 子句之类的东西,但遇到了困难。

框架: 我想使用 4 个 Togglebuttons,这显然会给我返回“Togglebutton.ischecked()”一个真或假布尔值。据此,我想选择我的数据库的正确课程。 Togglebuttons 的值是“Basic”、“Common”、“Uncommon”和“Rare”。 如果按下 Togglebuttons,它会调用 DB 方法,然后使用数据库的数据设置我的布局。

问题: 我在创建正确的查询时遇到问题,该查询会相应地更改 whereArguments 和 whereClause。根据我的理解 whereClause 需要一个 String 而 whereSelection 需要一个 StringArray。

我尝试了什么:

  1. 我尝试相应地创建一个 StringArray,这会产生固定索引的问题。因此,我在创建智能逻辑时遇到了问题,该逻辑会产生正确的 StringArray,

例如如果 ToggleButton (tb) tbBasic = true, tbUncommon = false, tbCommon = true, tbRare = true, 我需要类似 String[] whereArgs = new String[] {"Basic","Common","Rare"} 而我无法使用类似“添加”方法的方法相应地创建它。

  1. 因此,我尝试使用 Arraylist,它可以根据切换非常轻松地进行添加和删除。

例如如果我的 DBHelper 方法 getAllHeros 被调用,我可以每次创建一个新的 Arraylist,这会产生正确的 whereArgs。

ArrayList<String> whereArgsList = new ArrayList<>();

        if(btnBasic){
            whereArgsList.add("Basic");
        }
        if(btnCommon){
            whereArgsList.add("Common");
            }
        if(btnUncommon){
            whereArgsList.add("Uncommon");
        }
        if(btnRare){
            whereArgsList.add("Rare");
        }
    Cursor c = db.query("TableHeros", null,whereClause, whereArgsList.toArray(new String[0]),null,null,null,null);

问题在于显然 whereClause 也必须相应更新。因此,在 Arraylist 比一个 Element 长的情况下, whereClause 也需要相同数量的元素。

我希望我的观点很清楚,我愿意尝试任何建议

【问题讨论】:

  • 您当前对db.query 的调用似乎没有选择任何列,也不清楚基础查询应该是什么。您可以将您想要的原始 SQLite 查询添加到问题中吗?
  • @TimBiegeleisen SQLiteDatabase 的查询方法的第二个参数指定列,null 等于 *(所有列)。底层 SQL/查询将是 SELECT * FROM TableHeros ........
  • @MikeT 谢谢,不知道。但是关于whereClause
  • @TimBiegeleisen 是的,需要澄清 WHERE 子句需要什么切换是针对单个列还是单个列,以及是否应该使用 AND 或 OR,甚至可能是 IN 或 NOT IN .
  • @MikeT,我总是想要所有列,这就是我没有真正指定的原因。对不起 :)。所以使用 null 来获取所有列就好了

标签: android mysql sql sqlite togglebutton


【解决方案1】:

您尚未指定 WHERE 子句的外观。但是假设:

  • a) 按钮都适用于单个列(COL_TASK_TITLE(相当于字符串标题)在下面的代码中使用)和
  • b) 如果多个按钮为真,您希望选择同时包含值和的行
  • c) 还假设如果没有选择您想要所有行,那么以下内容可能与您想要的行一致

:-

public Cursor getMyRows(boolean btnBasic, boolean btnCommon, boolean btnUncommon, boolean btnRare) {

    ArrayList<String> whereArgsList = new ArrayList<>();
    String whereclause = null;
    String[] whereargs = null;

    if(btnBasic){
        whereArgsList.add("Basic");
    }
    if(btnCommon){
        whereArgsList.add("Common");
    }
    if(btnUncommon){
        whereArgsList.add("Uncommon");
    }
    if(btnRare){
        whereArgsList.add("Rare");
    }
    StringBuilder whereclauseToBe = new StringBuilder();
    for(String s: whereArgsList) {
        if (whereclauseToBe.length() > 1) {
            whereclauseToBe.append(" OR ");
        }
        whereclauseToBe.append(COL_TASK_TITLE); //<<<<<<<<< change to your column
        whereclauseToBe.append(" = ? ");
    }
    if (whereclauseToBe.length() < 1) {
        Log.d("WHERE CLAUSE","No selections so WHERE CLAUSE and WHERE ARGS have been set as null");
    } else {
        whereclause = whereclauseToBe.toString();
        Log.d("WHERE CLAUSE ", "The generated WHERE CLAUSE would be... WHERE " + whereclauseToBe.toString());
    }
    if (whereArgsList.size() > 0) {
        whereargs = new String[whereArgsList.size()];
        whereargs = whereArgsList.toArray(whereargs);
    }

    SQLiteDatabase db = this.getWritableDatabase();
    Cursor c =  db.query(TABLE, null,whereclause, whereargs ,null,null,null,null); //<<<<<<<<<< Change TABLE to table name
    return c; //<<<<<<<<<< Could just do `return db.query(TABLE.........`
}
  • 请注意,这是 SQLiteOpenHelper (即数据库助手)子类中的一个方法。

以上是使用(来自活动)进行测试的:-

    db.getMyRows(false,false,false,false);
    db.getMyRows(true,false,false,false);
    db.getMyRows(true,false,true,false);
    db.getMyRows(false,true,true,false);
    db.getMyRows(false,false,false,true);
    db.getMyRows(true,true,true,true);

写入日志的结果是:-

10-22 04:44:23.975 1429-1429/? D/WHERE CLAUSE: No selections so WHERE CLAUSE and WHERE ARGS have been set as null
10-22 04:44:23.975 1429-1429/? D/WHERE CLAUSE: The generated WHERE CLAUSE would be... WHERE title = ? 
10-22 04:44:23.975 1429-1429/? D/WHERE CLAUSE: The generated WHERE CLAUSE would be... WHERE title = ?  OR title = ? 
10-22 04:44:23.975 1429-1429/? D/WHERE CLAUSE: The generated WHERE CLAUSE would be... WHERE title = ?  OR title = ? 
10-22 04:44:23.975 1429-1429/? D/WHERE CLAUSE: The generated WHERE CLAUSE would be... WHERE title = ? 
10-22 04:44:23.975 1429-1429/? D/WHERE CLAUSE: The generated WHERE CLAUSE would be... WHERE title = ?  OR title = ?  OR title = ?  OR title = ? 
  • 注意 TABLE 和 COL_TASK_TITLE 来自表,需要更改。

【讨论】:

  • 嘿@MikeT,感谢您的回答。经过测试,我又发现了一个错误。我们不能对空对象进行 toString()。因此,我将 whereClausetoBe.toString 更改为能够处理空对象的 String.valueof(whereClausetoBe)。但我真的不知道如何解决 Arraylist 的问题。是否还有一种聪明的方法可以不调用空对象而不是使用 try 和 catch?
  • @Christian.gruener 哎呀将看看。没有测试 Cursor 方面,因为那将是相当多的工作。
  • @Christian.gruener 已经编辑了答案,这也已经过测试,尽管在现有表/列上进行测试时没有返回任何行。
  • 谢谢先生!这完全解决了我的问题! :) 将不胜感激我的问题 ;)
猜你喜欢
  • 2018-08-04
  • 2018-11-01
  • 2021-07-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-08-14
  • 2020-01-04
相关资源
最近更新 更多