在iPhone

时间:2016-01-20 19:24:29

标签: iphone sqlite ios-simulator

我已尝试使用预备语句和常规语句,使用长iPhone模拟器路径从我的表中检索记录。

我根本无法获得在WHERE语句中使用字段Path的SELECT语句。如果我删除WHERE语句,它将返回记录。

e.g。

Last Added[/Users/admin/Library/Developer/CoreSimulator/Devices/1546523B-D9E4-45F6-9ACA-ADA5CF73DFE4/data/Containers/Data/Application/9187662E-16F3-4573-B486-256BDA00CBD1/Documents/wf_mages-3.lha]

SQL[SELECT ID FROM Tune  WHERE Path="/Users/admin/Library/Developer/CoreSimulator/Devices/1546523B-D9E4-45F6-9ACA-ADA5CF73DFE4/data/Containers/Data/Application/9187662E-16F3-4573-B486-256BDA00CBD1/Documents/wf_mages-3.lha"]

我在查询中尝试了双引号和单引号。我甚至在SQLiteBrowser中尝试了相同的查询,它运行正常。

SELECT ID FROM Tune WHERE路径LIKE'%mages%'工作正常。

正斜杠或路径值的大小有问题吗?需要以某种方式逃避正斜杠吗?

我能找到的关于正斜线的唯一其他帖子建议使用的预备语句,但这是我最初的开始并且它们不起作用。查找在我的表中的任何其他字段上都可以正常工作 - 只是不是路径。

int GetTuneIDWithPath( char *pszPath )
{
  // TEST
  char   txTmp   [ 1024 ];

  sprintf( g_txSQL, "SELECT %s", fldTune_ID );

  sprintf( txTmp, " FROM %s ", tbTune );
  strcat( g_txSQL, txTmp );

  //sprintf( txTmp, " WHERE %s=\"%s\"", fldTune_Path, pszPath );
  //strcat( g_txSQL, txTmp );

//  sprintf( txTmp, " WHERE %s='%s'", fldTune_Path, pszPath );
  //strcat( g_txSQL, txTmp );

  //sprintf( txTmp, " WHERE %s LIKE '%%mages%%'", fldTune_Path );
  //strcat( g_txSQL, txTmp );

  LogDebugf( "SQL[%s]", g_txSQL );

  char  *zErrMsg = 0;
  char **pszResult;
  int    nRows;
  int    nCols;
  int    rc;

  rc = sqlite3_get_table_wrapper( g_MainDB,
                                 g_txSQL,
                                 &pszResult,
                                 &nRows,
                                 &nCols,
                                 &zErrMsg );

  if( nRows != 1 )
  {
    LogDebugf( "FAILED nRows: %d", nRows );
    return FALSE;
  }

  // First row is field names, so start at 1
  int nCol = 0;
  int nID = Safe_atoi(    pszResult[ nCols + nCol ] );  nCol ++;

  LogDebugf( "PDS> nID: %d Find[%s]", nID, pszPath );  
  return nID;
}

在此之前,我确实尝试使用像我一样的准备语句用于其他查询:

  char   txTmp   [ 1024 ];

  sprintf( g_txSQL, "SELECT %s", fldTune_ID );    
  sprintf( txTmp, " FROM %s WHERE %s=?", tbTune, fldTune_Path );
  strcat( g_txSQL, txTmp );

  sqlite3_stmt *stmt = NULL;  
  sqlite3_prepare( g_MainDB, g_txSQL, -1, &stmt, NULL );
  sqlite3_reset( stmt );
  sqlite3_bind_text( stmt,  1, pszPath, strlen( pszPath ), SQLITE_STATIC );

  rc = sqlite3_step( stmt );

  if( rc != SQLITE_ROW ) 
  {
    LogDebugf( "PDS> Lookup failed [%s] rc: %d", pszPath, rc );
    return FALSE;
  }

  int nID = sqlite3_column_int( stmt, 0 );

  LogDebugf( "PDS> nID: %d Find[%s]", nID, pszPath );

1 个答案:

答案 0 :(得分:2)

您需要忽略文件的实际位置,并且只记录和搜索应用程序文档目录中的文件,因此您需要存储/搜索'wf_mages-3.lha'而不是{{ 1}}。

只有在实际读取/写入文件时,您才需要在文档路径前加上'/Users/admin/Library/Developer/CoreSimulator/Devices/1546523B-D9E4-45F6-9ACA-ADA5CF73DFE4/data/Containers/Data/Application/9187662E-16F3-4573-B486-256BDA00CBD1/Documents/wf_mages-3.lha'

原因是该位置将在应用更新期间发生变化,文档目录内容将被迁移,但数据库行不会被迁移,您将失去两者之间的连接。

在语句中使用NSSearchPathForDirectoriesInDomains()应该没有问题,因为就SQL而言它并不特殊,所以应该可以在文档文件夹中创建一个层次结构而没有问题。

要对您的代码发表评论,我以前从未见过这种方法,我会提倡更传统的'/'sqlite3_prepare()sqlite3_step()函数。此外,最重要的是,您需要使用sqlite3_finalize()报告任何错误,否则您将无法取得任何进展。