Чтение и запись изображений на БД SQLite для использования iPhone

голоса
22

Я создал БД SQLite , который в настоящее время чтения и записи NSStringСплошной. Я также хочу , чтобы сохранить изображение в базе данных и вспомнить его позже. Я прочитал немного об использовании NSDataи кодирования изображения, но я не совсем уверен , что синтаксис для того, что я хочу сделать. Любые фрагменты кода или примеры было бы весьма признателен.

Мой текущий процесс выглядит следующим образом : UIImagePickerController-> Пользователь выбирает изображение из фотографий -> chosenImage установлен на экземпляр UIImageView-> Теперь я хочу взять это изображение и сохранить его в БД

Я должен упомянуть, этот вызов будет в конечном итоге заменить вызов на удаленный сервер. Не уверен, если это делает разницу, насколько производительность идет.

Задан 13/03/2009 в 18:03
источник пользователем
На других языках...                            


6 ответов

голоса
31

Вам нужно преобразовать UIImage размещенного внутри вашего UIImageView в блобы для хранения в SQLite. Чтобы сделать это, вы можете использовать следующее:

NSData *dataForImage = UIImagePNGRepresentation(cachedImage);
sqlite3_bind_blob(yourSavingSQLStatement, 2, [dataForImage bytes], [dataForImage length], SQLITE_TRANSIENT);

Это будет генерировать представление PNG вашего изображения, сохранить его в экземпляре NSData, а затем связать байты из NSData как BLOB для второго аргумента в вашем SQL запросе. Используйте UIImageJPEGRepresentation в выше, чтобы сохранить в этом формате, если вы хотите. Вам нужно будет иметь столбец BLOB добавлен к соответствующей таблице в базе данных SQLite.

Чтобы получить это изображение, вы можете использовать следующее:

NSData *dataForCachedImage = [[NSData alloc] initWithBytes:sqlite3_column_blob(yourLoadingSQLStatement, 2) length: sqlite3_column_bytes(yourLoadingSQLStatement, 2)];       
self.cachedImage = [UIImage imageWithData:dataForCachedImage];
[dataForCachedImage release];
Ответил 13/03/2009 в 18:41
источник пользователем

голоса
9

Рекомендация от Apple не хранить BLOB-й в SQLite баз данных, которые больше, чем ~ 2 килобайта.

SQLite организует базы данных на страницы. Каждая страница 4 килобайта. При считывании данных из файла базы данных SQLite он загружает эти страницы во внутренний кэш страниц. На iPhone я думаю, что этот кэш по умолчанию 1 мегабайта в размере. Это делает чтение соседних записей очень быстро, потому что они, вероятно, будут в кэше страниц уже.

Когда SQLite считывает записи из базы данных в памяти, она считывает всю запись и все страницы, которые он занимает. Так что, если ваша запись содержит BLOB, это может занять много страниц, и вы будете выбрасывания существующих страниц из кэша и замены их страниц вашего BLOb пластинки.

Это не так уж плохо, если вы просто сканировать через и загружая все ваши BLOBS, чтобы сделать что-то с ними (их отображения, например). Но если сказать, что вы сделали запрос, где вы просто хотели, чтобы получить некоторые данные, которые в той же строке, что и BLOB этот запрос будет гораздо медленнее, чем если запись не содержит большой BLOB.

Таким образом, как минимум, вы должны хранить данные BLOB в отдельной таблице. Например:

CREATE TABLE blobs ( id INTEGER PRIMARY KEY, data BLOB );
CREATE TABLE photos ( id INTEGER PRIMARY KEY, name TEXT, blob_id INTEGER, 
    FOREIGN KEY(blob_id) REFERENCES blobs(id) );

Или еще лучше, хранить данные BLOB в виде файлов вне базы данных SQLite.

Обратите внимание , что это может быть возможным , чтобы настроить размер кэша страницы с заявлением SQL Pragma (если вы не используете CoreData).

Ответил 15/04/2011 в 11:21
источник пользователем

голоса
9

Один из вариантов (и обычно предпочтительно при работе в SQL), чтобы записать изображение в файл в системе и сохранить путь (или какой-либо другой вид идентификатора) в базе данных.

Ответил 13/03/2009 в 18:32
источник пользователем

голоса
2

Запись изображения в БД SQLite

if(myImage != nil){
    NSData *imgData = UIImagePNGRepresentation(myImage);
    sqlite3_bind_blob(update_stmtement, 6, [imgData bytes], [imgData length], NULL);    
    }
    else {
        sqlite3_bind_blob(update_stmtement, 6, nil, -1, NULL);
    }

Чтение из БД SQLite:

NSData *data = [[NSData alloc] initWithBytes:sqlite3_column_blob(init_statement, 6) length:sqlite3_column_bytes(init_statement, 6)];
        if(data == nil)
            NSLog(@"No image found.");
        else
            self.pictureImage = [UIImage imageWithData:data];   
Ответил 29/01/2010 в 14:05
источник пользователем

голоса
0

Вы должны сначала написать файл в файловой системе. а затем на пути изображения и сохранить этот путь изображения (URL) в виде текста в SQLite.

Ответил 27/05/2015 в 07:08
источник пользователем

голоса
0

Лучше всего, чтобы сжать изображение и сохранить его в базе данных системы или файла. Если вы не заботитесь о разрешении изображения вы можете пойти вперед и даже изменить размер изображения с помощью:

   UIGraphicsBeginImageContext(newSize);  
   [image drawInRect:CGRectMake(0,0,newSize.width,newSize.height)];   
   UIImage* newImage = UIGraphicsGetImageFromCurrentImageContext();    
   UIGraphicsEndImageContext();

После этого вы можете использовать UIImageJPEGRepresentationдля изображений в формате JPEG со значением «0» для максимального сжатия. Или вы можете использовать UIImagePNGRepresentationдля PNG изображений

Ответил 05/07/2012 в 13:21
источник пользователем

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more