Este es mi código para mi aplicación de prueba donde quiero mostrar a los usuarios en el siguiente controlador de vista, pero cuando ejecuto e intento recuperar los valores, me están dando valores repetidos. he utilizado NSMutableDictionary
y NSMutableArray
.
#import "DBManager.h"
static DBManager *sharedInstance = nil;
static sqlite3 *database = nil;
static sqlite3_stmt *statement = nil;
@implementation DBManager
-(void) getsaveData:(NSString *)Username
{
const char *dbpath = [newFileAtPath UTF8String];
NSMutableArray *userArray = [[NSMutableArray alloc]init];
if (sqlite3_open(dbpath, &database)==SQLITE_OK) {
NSMutableDictionary *userInfo = [[NSMutableDictionary alloc] init];
NSString *getSQL = [NSString stringWithFormat:@"SELECT * FROM USERS WHERE USERNAME != "%@"",Username];
const char *retrievestmt = [getSQL UTF8String];
if(sqlite3_prepare_v2(database, retrievestmt, -1, &statement, NULL)==SQLITE_OK)
{
while(sqlite3_step(statement)==SQLITE_ROW)//in this while loop i am getting repeated values
{
NSString *User_ID = [[NSString alloc] initWithUTF8String: (const char *) sqlite3_column_text(statement, 0)];
[userInfo setObject:User_ID forKey:@"ID"];
//[userArray addObject:User_ID];
NSString *User_Email = [[NSString alloc] initWithUTF8String:(const char *) sqlite3_column_text(statement, 1)];
[userInfo setObject:User_Email forKey:@"Email"];
//[userArray addObject:User_Email];
NSString *Password = [[NSString alloc] initWithUTF8String:(const char *) sqlite3_column_text(statement, 2)];
[userInfo setObject:Password forKey:@"Email"];
//[userArray addObject:Password];
NSString *User_name = [[NSString alloc] initWithUTF8String:(const char *) sqlite3_column_text(statement, 3)];
[userInfo setObject:User_name forKey:@"Username"];
//[userArray addObject:User_name];
NSString *User_Avatar = [[NSString alloc] initWithUTF8String:(const char *) sqlite3_column_text(statement, 4)];
[userInfo setObject:User_Avatar forKey:@"Avatar"];
//[userArray addObject:User_Avatar];
[userArray addObject:userInfo];
NSLog(@"userArray %@",userArray);
}
sqlite3_reset(statement);
}
}
}
@end
En el while
loop estoy geeting el error.
Intenté varias veces con múltiples soluciones, por favor, ayúdame a arreglar esto.
Respuestas
2 para la respuesta № 1El problema es simple: está reutilizando incorrectamente el userInfo
diccionario. Es necesario crear una nueva instancia en cada iteración de bucle.
Mueve la línea:
NSMutableDictionary *userInfo = [[NSMutableDictionary alloc] init];
justo después de la while
línea de bucle.
También tienes muchos otros problemas con tu código:
- Nunca cierras la base de datos.
- Nunca finalizas la declaración preparada.
- Restablece innecesariamente la declaración preparada.
- Usted tiene insuficiente comprobación / registro de errores.
- No está utilizando las convenciones de nomenclatura estándar.
- No está utilizando espacios en blanco estándar, lo que hace que su código sea más difícil de leer.
- Usted no usa la colocación consistente de llaves. Elija un estilo y utilícelo en todas partes.
- Estás utilizando variables estáticas cuando no deberías.
- Nunca compile sentencias SQL usando
stringWithFormat:
. Enlazar adecuadamente los valores a la consulta. - Nunca usar
SELECT *
en una consulta. Enumere explícitamente las columnas para asegurarse de obtener valores de columna consistentes y esperados.
Aquí está tu código actualizado para estos problemas:
#import "DBManager.h"
static DBManager *sharedInstance = nil;
@implementation DBManager
- (void)getsaveData:(NSString *)username {
const char *dbpath = [newFileAtPath UTF8String];
NSMutableArray *userArray = [[NSMutableArray alloc] init];
sqlite3 *database;
if (sqlite3_open(dbpath, &database) == SQLITE_OK) {
const char *retrievestmt = "SELECT USER_ID, USER_EMAIL, PASSWORD, USER_NAME, USER_AVATAR FROM USERS WHERE USERNAME != ?"; // replace * with actual column names
sqlite3_stmt *statement;
if (sqlite3_prepare_v2(database, retrievestmt, -1, &statement, NULL) == SQLITE_OK) {
sqlite3_bind_text(statement, 1, [username UTF8String], -1, SQLITE_TRANSIENT);
while (sqlite3_step(statement) == SQLITE_ROW) {
NSMutableDictionary *userInfo = [[NSMutableDictionary alloc] init];
NSString *userID = [[NSString alloc] initWithUTF8String:(const char *)sqlite3_column_text(statement, 0)];
userInfo[@"ID"] = userID;
NSString *userEmail = [[NSString alloc] initWithUTF8String:(const char *)sqlite3_column_text(statement, 1)];
userInfo[@"Email"] = userEmail;
NSString *password = [[NSString alloc] initWithUTF8String:(const char *)sqlite3_column_text(statement, 2)];
userInfo[@"Password"] = password;
NSString *username = [[NSString alloc] initWithUTF8String:(const char *)sqlite3_column_text(statement, 3)];
userInfo[@"Username"] = username;
NSString *userAvatar = [[NSString alloc] initWithUTF8String:(const char *)sqlite3_column_text(statement, 4)];
userInfo[@"Avatar"] = userAvatar;
[userArray addObject:userInfo];
}
sqlite3_finalize(statement);
NSLog(@"userArray %@",userArray);
} else {
NSLog(@"Unable to prepare the statement at %s: %s", retrievestmt, sqlite3_errmsg(database));
}
sqlite3_close(database);
} else {
NSLog(@"Unable to open the database at %@: %s", dbpath, sqlite3_errmsg(database));
}
}
@end