DBAtlas · Veritabanı operasyon atlası

LATERAL / CROSS APPLY (satır bazlı alt sorgu)

Oracle

-- Her müşterinin en son 3 siparişi (LATERAL, 12c+)
SELECT m.ad, s.tarih, s.tutar
FROM musteri m,
     LATERAL (SELECT tarih, tutar FROM siparis
              WHERE musteri_id = m.id
              ORDER BY tarih DESC FETCH FIRST 3 ROWS ONLY) s;

-- Alternatif: CROSS APPLY (12c+)
SELECT m.ad, s.tutar
FROM musteri m
CROSS APPLY (SELECT tutar FROM siparis WHERE musteri_id = m.id) s;

LATERAL/APPLY, FROM içindeki bir alt sorgunun soldaki tablonun sütunlarına başvurabilmesini sağlar; böylece 'her satır için ilk N kayıt' gibi ilişkili birleştirmeler yazılır. Oracle 12c hem ANSI LATERAL hem de CROSS/OUTER APPLY söz dizimini destekler.

PostgreSQL

SELECT m.ad, s.tarih, s.tutar
FROM musteri m
CROSS JOIN LATERAL (
  SELECT tarih, tutar FROM siparis
  WHERE musteri_id = m.id
  ORDER BY tarih DESC LIMIT 3
) s;

PostgreSQL LATERAL anahtar kelimesiyle (JOIN LATERAL / CROSS JOIN LATERAL / LEFT JOIN LATERAL) soldaki satıra bağlı alt sorgular yazılır. 'Her grup için ilk N' (top-N-per-group) ve set döndüren fonksiyonlarla satır genişletme için çok kullanışlıdır. CROSS APPLY söz dizimi yoktur; LATERAL kullanılır.

MySQL

-- MySQL 8.0.14+ LATERAL destekler
SELECT m.ad, s.tutar
FROM musteri m
JOIN LATERAL (
  SELECT tutar FROM siparis
  WHERE musteri_id = m.id
  ORDER BY tarih DESC LIMIT 3
) s ON true;

MySQL 8.0.14'ten beri LATERAL türetilmiş tabloları destekler; alt sorgu dıştaki tablonun sütunlarına başvurabilir. Öncesinde ve CROSS APPLY için karşılık yoktu; 'her grup için ilk N' pencere fonksiyonları veya ilişkili alt sorgularla çözülürdü. MariaDB'de LATERAL henüz yoktur.

SQL Server

SELECT m.ad, s.tarih, s.tutar
FROM musteri m
CROSS APPLY (
  SELECT TOP 3 tarih, tutar FROM siparis
  WHERE musteri_id = m.id
  ORDER BY tarih DESC
) s;
-- Eşleşme olmayanları da döndürmek için OUTER APPLY

SQL Server'ın LATERAL karşılığı APPLY operatörüdür: CROSS APPLY (INNER JOIN LATERAL gibi, eşleşmeyeni eler) ve OUTER APPLY (LEFT JOIN LATERAL gibi, eşleşmeyende NULL). Tablo değerli fonksiyonları her satır için çağırmakta ve top-N-per-group sorgularında yaygındır.

MongoDB

// En yakın karşılık: alt pipeline'lı $lookup
db.musteri.aggregate([
  { $lookup: {
      from: "siparis",
      let: { mid: "$id" },
      pipeline: [
        { $match: { $expr: { $eq: ["$musteri_id", "$$mid"] } } },
        { $sort: { tarih: -1 } }, { $limit: 3 }
      ],
      as: "son3"
  } }
])

MongoDB'de LATERAL/APPLY karşılığı, alt pipeline ve let değişkenleri olan $lookup biçimidir: dıştaki belgenin alanları let ile $$degisken olarak alt pipeline'a taşınır ve orada eşleşme/sıralama/sınırlama yapılır. Bu, 'her belge için ilgili ilk N' desenini çözer.

Redis

# Uygulanamaz: Redis'te alt sorgu / LATERAL yoktur.

Redis satır bazlı ilişkili alt sorgu sunmaz. 'Her öğe için ilgili ilk N' deseni uygulama tarafında döngüyle (her anahtar için ayrı ZRANGE gibi) veya sunucu tarafı Lua script ile çözülür.

Elasticsearch

# En yakın karşılık: terms + top_hits alt agregasyonu
GET siparis/_search
{
  "size": 0,
  "aggs": { "musteriye_gore": { "terms": { "field": "musteri_id" },
    "aggs": { "son3": { "top_hits": {
      "sort": [ { "tarih": "desc" } ], "size": 3 } } } } }
}

Elasticsearch'te LATERAL/APPLY yoktur; 'her grup için ilk N kayıt' deseni terms agregasyonu içine yerleştirilmiş top_hits alt agregasyonuyla elde edilir. Bu, ilişkili alt sorgu yerine tek index üzerinde gruplama artı grup içi örnekleme yaklaşımıdır.

DBAtlas'ta aç →