Etiket tabanlı verimli aramalara izin veren veri yapısı


11

Aşağıdakilere benzer verilerin depolanması için yüksek verimli bir veri yapısı arıyorum.

Kimlik Etiketleri Order1 Order2 
--------------------------
1 1,2 1 1
2 2,5 2 3
3 1,7 4 7
4 6 3 0

Destek ANDve ORve NOTişlemleri - bir ifade ifadesi içeren tüm kimlikleri listesini verecek şekilde bu yapı sorgulamak gerekir . Örneğin. ((1 veya 2) ve 7 değil)

Ayrıca sonuçların sırasını (Order1 veya Order2) belirleyebilmem ve isteğe bağlı bir ofsetle döndürülen maksimum satırları belirleyebilmem gerekiyor. İlk 30-100 sonuçların getirilmesi için performans önemlidir.

Son olarak, "etiket ilişkileri" aramak için ucuz bir yol gerekir örneğin hangi etiketleri "1" 2 ile ilgili etiketleri ve hangi sıklıkta "bilmek" istiyorum. Hangi etiketlerin frekansa göre sıralı olarak 1 VEYA 2 ... ile aynı sette göründüğü anlamına gelir.

Bu tür işler için hangi veri yapısının (veya yapı kümesinin) yüksek verimli olacağına dair herhangi bir fikriniz var mı?

(Bunu , SE site ailesinin etiketli sayfalarını yeniden tasarlamak için bir kavram kanıtı olarak kullanmak istiyorum )


1
Sadece bir yorum (belki de önemsiz). Neden ilişkisel bir veritabanı yönetim sistemine güvenmiyorsunuz? <İd, tag> çiftleri içeren bir tablo tanımlayabilir ve etiket sütununa bir dizin ekleyebilirsiniz. Sonra veri ayıklamak için standart SQL sorguları kullanabilirsiniz. RDBMS etkin bir şekilde sorgu optimizasyonu ve çıktı sıralaması "kirli" çalışmasını yapacak.
Marzio De Biasi

@Veya, ifadeler yüksek ölçekte inanılmaz derecede verimsiz, öz birleşimler kabus sorguları haline geliyor.
Sam Saffron

@Sam: tamam. Göreviniz oldukça yaygındır, bu yüzden iyi bir RDBMS (bir veri madenciliği aracıyla) işi yapabileceğini düşündüm. Zemini bir veri yapısı uzmanına bırakıyorum. :-)
Marzio De Biasi

Tüm VE, OR, NOT kombinasyonlarına izin vermek, tüm öğeler arasında listelenmeyen bir veri yapısı oluşturmayı zorlaştıracağına inanıyorum (belki 3-CNF ile sınırlı olabilir?). Böyle bir sınırlama yoksa, etiket gereksinimlerinizi geçen 30-100'ü bulana kadar belki de (belirtilen sırada) kayıtları çalıştırın. Genel olarak, Vor'un sizin için ağır kaldırma yapmak için bir veritabanı kullanma önerisine katılıyorum.
bbejot

Bir uzman değil, ama etiketleri sorma yolunda bazı kısıtlamalar koymazsanız, o zaman zor olacak. Bunları CNF'lerle sınırlamak (bbejot'un önerdiği gibi) bir yoludur, diğeri, sorgunun küçük bir sayı ile sorabileceği farklı etiketlerin sayısını kısıtlamaktır (6 diyelim).
Kaveh

Yanıtlar:


6

Bu tam olarak etkili bir veri yapısının cevabı değil, mevcut soruya göre neden daha iyi bir şey beklemememiz gerektiğine dair el sallayan bir argüman veren @bbejot ve @Kaveh yorumlarının detaylandırılmasıdır. tüm veritabanı. Argüman, SAT'dan bir azalmaya, üstel zaman hipotezine ve çok fazla el sallamaya dayanır .

nx|x|=nxj=1jxj=012nkkANDORNOTn2n

Sorgunun uzunluğunda etkili bir arama beklememeliyiz (SAT'a indirgeyerek). Ayrıca, üstel zaman hipoteziyle veritabanındaki tüm öğelere bakmaktan daha iyi beklememeliyiz.

n1


İyi gözlem. Her sorunun en fazla 5 etiketi vardır, bu nedenle etiketlerle ilgili bir sorgu 5-CNF'ye eşdeğerdir.
Kaveh

teşekkür ederim! evet burada daha fazla 5-CNF olduğunu varsayabiliriz, etiketleme davranışı rastgele değildir. Genelde insanlar en yaygın etiketlerle bir şeyler etiketleyecektir, böylece birkaç kısayol daha kullanılabilir.
Sam Saffron

1
@Kaveh, bir hafıza yapısında yuvarlandık. Birkaç önemsiz olmayan kısayol vardır, sıralama bir darboğazdır, yığın sıralaması veya değiştirilmiş bir hızlı sıralama, tam bir sıralama yapmanıza gerek kalmadan üst N'yi etkili bir şekilde seçmenizi sağlar. ön hesaplamalar, tam bir tarama gerektiğinde pivotları daha verimli seçmenize ve türlerden kaçınmanıza olanak tanır. çoklu kullanım seçimleri hızlandırır. kullanıcılar yapılarla etkileşime girmeden önce arka plana çok fazla iş ertelenebilir. şaşırtıcı şekilde bellek içi yapılarımız, yığın taşması veri kümesinde arama yapmak için ortalama 0 ms'dir.
Sam Saffron

@SamSaffron - Bu özelliği detaylandıran MSO yazısı nerede? Burada bir hata raporumuz var .
Kevin Vermeer

5

Bu oldukça basit bir cevap ama etkili olduğunu düşünüyorum:

Map Tag ([Id],[Id])O(log(n))

Map Id (Set Tag)IdO(nlog(m))


Birden fazla kez biriktirilmiş bir harita gibi bazı çok basit yapıların buraya gitmenin en iyi yolu olabileceğini kabul etme eğilimindeyim. bellek ucuz ve birden çok önbellek korumak çok zor değil
Sam Saffron
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.