PostgreSQL setara dengan variabel kueri MySQL?

9

Apakah ada cara mudah untuk mengadaptasi jenis-jenis pertanyaan MySQL ini ke PostgreSQL:

  1. pengaturan variabel di MySQL suka

    set @aintconst = -333
    set @arealconst = -9.999

    Sepertinya tidak .

  2. Menetapkan variabel dari kueri SELECT dan menggunakan variabel-variabel tersebut selanjutnya dalam SQL saya seperti:

     select @pfID := id from platform where bios like '%INTEL%'
     select @clientID := id from client where platformID = @pfID

Saya akan sangat berterima kasih untuk petunjuk, terutama pada (2).

Daniel
sumber
Anda mungkin menemukan variabel PSQL adalah apa yang Anda cari. dba.stackexchange.com/a/213009/2639
Evan Carroll

Jawaban:

13

Ini mudah dilakukan di dalam fungsi PL / pgSQL (atau blok DO ):

create function myfunc() returns void language plpgsql as $$
  declare
    aintconst constant int = -333;
    arealconst constant real = -9.99;
    pfid int;
    clientid int;
  begin

    select id from platform where bios like '%INTEL%' into pfid;

    select id from client where platformID = pfid into clientid;

  end $$;

Anda juga dapat menggunakan variabel GUC :

--set a session variable
set mycustom.var = 'value';

--use it
select * from mytable where some_column = current_setting('mycustom.var');

Atau Anda dapat menggunakan CTE dengan bergabung:

with myvars as (
  select
    -333::int as aint,
    -9.99::real as areal
)

select 
  a.*
from mytable a
join myvars on true
where
  a.thing = aint
Neil McGuigan
sumber
Jika Anda menggunakan metode GUC, bagaimana Anda mengatur variabel dengan daftar angka yang disebutkan?
user952342
9

Saya menggunakan DENGAN pernyataan:

WITH vars as (SELECT -333::double precision as aintconst,-9.999::double precision as arealconst)
UPDATE table SET col1 = (SELECT aintconst FROM vars)

dan:

WITH platformx AS (SELECT id FROM platform WHERE bios like '%INTEL%')
SELECT id FROM client WHERE platformID = (SELECT id FROM platformx)
pengguna2641043
sumber
3

Anda sudah menjawabnya sendiri: Tidak, tidak ada dalam SQL biasa. Anda dapat menggunakan PL / PgSQL jika Anda ingin variabel, dalam suatu fungsi atau DOblok.

Sebagian besar penggunaan untuk variabel kueri di MySQL dipenuhi oleh CTE ( WITHkueri), fungsi jendela, dll dalam PostgreSQL.


Sebenarnya ada, tetapi mereka tidak cocok untuk penggunaan umum dalam kueri. Anda biasanya mengakses GUC khusus dengan SETdan SHOW, tetapi Anda bisa menggunakan:

regress=> select set_config('a.b', 'c', false);
 set_config 
------------
 c
(1 row)

regress=> select current_setting('a.b');
 current_setting 
-----------------
 c
(1 row)

GUC itu mahal dan itu ide yang buruk untuk menggunakan ini untuk permintaan tujuan umum, tetapi kadang-kadang ada penggunaan yang valid. Anda hanya dapat menggunakan pengaturan seperti myapp.variablejuga.

Craig Ringer
sumber
2

Variabel PSQL

Sejak setidaknya versi 7.1 klien PostgreSQL telah menyediakan fungsionalitas ini dengan psqlvariabel

\set aintconst  -333
\set arealconst -9.999

SELECT :aintconst AS aintconst, :arealconst AS realconst;
 aintconst | realconst 
-----------+-----------
      -333 |    -9.999
(1 row)

Pada dasarnya yang Anda inginkan adalah kemampuan untuk skrip SQL. PSQL memiliki persyaratan dan variabel, dan kemampuan untuk memberi umpan balik SQL yang dihasilkan secara dinamis yang membuat pekerjaan ini lebih mudah. Ini bukan fungsi sisi-server di dunia PostgreSQL, dan umumnya saya akan melakukan ini dalam bahasa klien (seperti Node.js atau Perl daripada di psql).

Evan Carroll
sumber
butuh pembaruan. karena Postgresql terbaru memungkinkan:SET LOCAL variable value
Eugen Konkov
1
Itu untuk parameter konfigurasi - itu hal yang sama sekali berbeda @EugenKonkov
Evan Carroll
1

Untuk contoh kedua Anda tidak perlu variabel (baik di MySQL maupun di Postgres):

select id 
from client 
where platformID in (select id 
                     from platform 
                     where bios like '%INTEL%');

Jangan takut pada sub-kueri, optimizer kueri Postgres jauh lebih pintar daripada MySQL.

Jika hal di atas terlalu lambat, menulis ulang menjadi existskueri terkadang lebih cepat:

select c.id 
from client c
where exists  (select 1
               from platform p
               where c.platformID = p.id
                 and bios like '%INTEL%');
seekor kuda tanpa nama
sumber