Çoğunlukla ikili ek verilerini depolayan bir BLOB sütunu content
dahil olmak üzere ileti eklerinde çoğunlukla bulunan bir ~ 90 MB veritabanı kullanıyorum.Neden 'IS NULL' 100x blob sütununda 'length() = 0' daha yavaş?
BLOB'lar üzerinde bir dizin oluşturmak akıllıca olmadığından, autoindex dışında hiçbir dizin içermez.
SELECT message_id FROM attachments WHERE content IS NULL;
ve benim USECASE aynı satırlar neden
SELECT message_id FROM attachments WHERE length(content) = 0;
:
boş ekleri almak için aşağıdaki querys karşılaştırıldı.
İlk neden 250 ms alır ve ikincisi sadece 1-2 ms'dir (her ikisi de SSD'de)? Bunun sebebi nedir? Gizli bir uzunluk indeksi mi var? Herhangi bir içgörü takdir edildi.
Ek bilgiler
her iki durumda da
EXPLAIN QUERY PLAN
olduğunu0 | 0 | 0 | TARAMA TABLOSU ekleri
olumsuzluk
IS NOT NULL
vs aynı performanstalength() != 0
sonuçları fark 250ms vs 2ms.- Yalnızca {NULL} sütun içerensütunları 250 ms ve
WHERE length(content) = 0 AND content IS NULL;
2 ms alır birleşik querys.
Karşılaştırmalarınızın doğru olduğundan emin misiniz? Veriler önbelleğe alınmış mıydı? Sqlite istemcisinin yeni bir örneğini başlattıktan sonra, önce ikinci sorguyu çalıştırırsanız ne olur? Ya da her sorguyu birkaç kez tekrarlayın, en hızlı koşuyu referans olarak alın. –
Bir veya daha fazla sqlite3 işleminde herhangi bir sırada hızlı ve yavaş sorgu sınırsız kez yeniden üretebilir. "Karşılaştırma doğru" ile ne demek istiyorsun? –
Bunun, sütun uzunluğunun depolandığından, yani uzunluk kontrolünün BLOB'un içeriğinin alınmasını gerektirmediği varsayılır. Yine de her kaydı taramanız gerekir, ancak NULL kontrolü için kayıt başına en az bir ek okuma var. Tabi ki, IS NULL kayıt uzunluğunu kullanmak için optimize edilmiş/olmalıdır. Https://www.sqlite.org/fileformat2'ye bir göz atın.html, özellikle "2.1 Kayıt Formatı" bölümü. –