objective-c - 如何在此代码中修复间接指针的转换(在ARC下)?

标签 objective-c xcode sqlite automatic-ref-counting

因此,我们试图遍历Lynda.com提供的实现NSFastEnumeration的SQLite示例。对我来说,将其转换为ARC一直是我的问题,因为我无法修复该错误

Cast of an indirect pointer to an Objective-C pointer to 'va_list' (aka char *) is      disallowed with ARC.


它指向此行和va_list强制转换

[self bindSQL:[query UTF8String] arguments:(va_list)values];


在定义了values的此函数中(添加了__unsafe_unretained来修复其他错误)

- (NSNumber *) insertRow:(NSDictionary *) record 
{
    int dictSize = [record count];
    __unsafe_unretained id values[dictSize];


bindSQL的实现是

- (void) bindSQL:(const char *) cQuery arguments:(va_list)args


如何纠正?

感谢您的关注。这里要求的是原始的bindSQL函数和调用insertRow函数

- (void) bindSQL:(const char *) cQuery arguments:(va_list)args {
// NSLog(@"%s: %s", __FUNCTION__, cQuery);
int param_count;

// preparing the query here allows SQLite to determine
// the number of required parameters
if (sqlite3_prepare_v2(database, cQuery, -1, &statement, NULL) != SQLITE_OK) {
    NSLog(@"bindSQL: could not prepare statement (%s)", sqlite3_errmsg(database));
    statement = NULL;
    return;
}

if ((param_count = sqlite3_bind_parameter_count(statement))) {
    for (int i = 0; i < param_count; i++) {
        id o = va_arg(args, id);

        // determine the type of the argument
        if (o == nil) {
            sqlite3_bind_null(statement, i + 1);
        } else if ([o respondsToSelector:@selector(objCType)]) {
            if (strchr("islISLB", *[o objCType])) { // integer
                sqlite3_bind_int(statement, i + 1, [o intValue]);
            } else if (strchr("fd", *[o objCType])) {   // double
                sqlite3_bind_double(statement, i + 1, [o doubleValue]);
            } else {    // unhandled types
                NSLog(@"bindSQL: Unhandled objCType: %s", [o objCType]);
                statement = NULL;
                return;
            }
        } else if ([o respondsToSelector:@selector(UTF8String)]) { // string
            sqlite3_bind_text(statement, i + 1, [o UTF8String], -1, SQLITE_TRANSIENT);
        } else {    // unhhandled type
            NSLog(@"bindSQL: Unhandled parameter type: %@", [o class]);
            statement = NULL;
            return;
        }
    }
}

va_end(args);
return;


}

- (NSNumber *) insertRow:(NSDictionary *) record {
// NSLog(@"%s", __FUNCTION__);
int dictSize = [record count];

// the values array is used as the argument list for bindSQL
id keys[dictSize];  // not used, just a side-effect of getObjects:andKeys
id values[dictSize];
[record getObjects:values andKeys:keys];    // convenient for the C array

// construct the query
NSMutableArray * placeHoldersArray = [NSMutableArray arrayWithCapacity:dictSize];
for (int i = 0; i < dictSize; i++)  // array of ? markers for placeholders in query
    [placeHoldersArray addObject: [NSString stringWithString:@"?"]];

NSString * query = [NSString stringWithFormat:@"insert into %@ (%@) values (%@)",
                    tableName,
                    [[record allKeys] componentsJoinedByString:@","],
                    [placeHoldersArray componentsJoinedByString:@","]];

[self bindSQL:[query UTF8String] arguments:(va_list)values];
sqlite3_step(statement);
if(sqlite3_finalize(statement) == SQLITE_OK) {
    return [self lastInsertId];
} else {
    NSLog(@"doQuery: sqlite3_finalize failed (%s)", sqlite3_errmsg(database));
    return [NSNumber numberWithInt:0];
}


}

最佳答案

看起来,当您传递bindSQL:arguments:数组时,您的va_list接受id

因此,ARC不知道如何处理从id*va_list的转换。如果它在打开ARC之前有效,那么很幸运,您的目标计算机上的某些内部表示形式匹配。但是即使没有ARC,您也无法确定它,因为它会意外地给您带来一些令人讨厌的崩溃。

关于objective-c - 如何在此代码中修复间接指针的转换(在ARC下)?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8660798/

相关文章:

iphone - 如何主题uitableview uiview和 friend

ios - 如何在 UITextView 中自动换行?

ios - 如何在 SearchBar 中使用 textDidChange 进行搜索

sqlite - 对第二个选择变量使用 DISTINCT

ios - UITableViewCell 滚动自定义 UITableView 标题标题

objective-c - NSInvocation & NSError - __autoreleasing & memory crasher

sqlite - 我在哪里可以找到 SQLite 数据库文件的示例或它的转储?

c++ - 如何在 C/C++ 中提交 SQLite 事务?

ios - UIViewController 自定义转换和状态恢复

iphone - 多次按下按钮会导致 ios cocoa 中的单一操作