Hirdetés
- D1Rect: Nagy "hülyétkapokazapróktól" topik
- Toomy: FOXPOST régen jó volt, de ma már jobban jársz ha elfelejted.
- sziku69: Fűzzük össze a szavakat :)
- Luck Dragon: Asszociációs játék. :)
- Gurulunk, WAZE?!
- btz: Internet fejlesztés országosan!
- gban: Ingyen kellene, de tegnapra
- sziku69: Szólánc.
- Sub-ZeRo: Euro Truck Simulator 2 & American Truck Simulator 1 (esetleg 2 majd, ha lesz) :)
- Magga: PLEX: multimédia az egész lakásban
Új hozzászólás Aktív témák
-
bpx
őstag
A kérdés az volt, hogy azok a sorok kellenek amelyek ID-ja csak egyszer szerepel a táblában, továbbá igaz rájuk, hogy status = open, type = 477.
Nálad a status = open, type = 477 szűrés az aggregráció előtt történik, mert az a WHERE-ben van, nem a HAVING-ben.
Emiatt ha pl. így néz ki a tábla, akkor az eredményedbe mindkettő sor bekerül:
id | status | type
--------|--------|------
1 | open | 477
1 | closed | 476Erre nem teljesül az, hogy az ID csak egyszer szerepel, hiszen 2 sorban is ott van, és mivel csak az ID alapján történik a self join, visszadja az ID-hoz tartozó összes többi sort is, amelyekre a status = open, type = 477 nem teljesül.
A min(status) meg min(type) részhez annyi, hogy a having count(*) miatt eleve csak az 1 tagú csoportokat vizsgáljuk, ahova mindegy, hogy min vagy max vagy más csoport függvényt írok, de valamit muszáj, hogy megegye az aggregráció + having. A havingben ott van utána még a számunkra szükséges szűrés, ez az aggregáció után történik, és az 1 elemű csoportokból csak a nekünk szükségeseket hagyja meg.
Szerintem a kérdés direkt van ilyen egyszerűre fogalmazva, hogy meg lehessen oldani subquery meg analitikus függvény nélkül.
-
bpx
őstag
Egy indexet több módon lehet használni.
Az oszlop1 like 'valami%' szűréshez megy az index range scan az oszlop1-en levő indexen. Ez hatékonyan működik.
Az oszlop1 like '%valami%' szűréshez szintén használható az oszlop1-en levő index, csak az már nem index range scan, hanem index fast full scan lesz, ahol az adatbázis a teljes indexet végigolvassa random sorrendben.
Az oszlop1 like '%valami%' szűréshez ha még egy order by oszlop1 is van, akkor pedig index full scan is használható, ahol az adatbázis a teljes indexet végigolvassa, de a fa struktúrát bejárva, rendezett sorrendben.
Tehát nem, nem lesz mindig full table scan, mert a 300 oszlopot tartalmazó táblára történő full scan helyett még mindig gyorsabb a csak 1 oszlopot tartalmazó és ezáltal sokkal kisebb méretű indexen a full scan.
De az utóbbi 2 már nem hatékony és ha nagy mennyiségű adaton kell szöveges keresést végrehajtani, akkor a like '%valami%' helyett ott van az Oracle Text a saját indexeivel és függvényeivel, meg a többi adatbázisnál is a text alapú indexek és keresések. -
bpx
őstag
Ezek az Oracle saját tanfolyamai. Mindenhol ennyi lesz az ára nagyságrendileg és a tananyag is ugyanaz lesz. Az Oracle Hungary az oktatási részlegét leépítette, az oktatási partnerek tartják nekik a tanfolyamokat.
Több helyen is vannak egyedileg egyeztetett tematikájú ás formátumú oktatások is. Ezek ár/értékben kedvezőbbek. Talán.
De igazából egyik változattal sem vagyok megelégedve.
Az említett Webváltónál dolgozom, 10 éve. Nem foglalkozom oktatással, csak ha nagyon muszáj.
-
bpx
őstag
Konstans értéket nem kell a group by-ban felsorolni.
De, tud alias alapján rendezni.
Nem, nem tud oszlopszám szerint csoportosítani.select
1 + 2 as harom,
null as ertek2,
created as letrehozva,
sum(user_id) as valami,
count(*) as darab,
'hello' as ertek3
from
dba_users
group by
created
order by
harom,
letrehozva
;
HAROM E LETREHOZVA VALAMI DARAB ERTEK
---------- - ------------------- ---------- ---------- -----
3 2020-04-16 19:04:45 6442450869 6 hello
3 2020-04-16 19:04:46 13 1 hello
3 2020-04-16 19:06:12 43 2 hello
3 2020-04-16 19:06:18 23 1 hello
3 2020-04-16 19:07:31 2147483638 1 hello
3 2020-04-16 19:08:08 36 1 hello
3 2020-04-16 19:15:29 48 1 hello
3 2020-04-16 19:15:31 49 1 hello
3 2020-04-16 19:15:37 101 2 hello
3 2020-04-16 19:18:29 61 1 hello
3 2020-04-16 19:18:41 62 1 hello
3 2020-04-16 19:20:21 70 1 hello
3 2020-04-20 20:51:53 73 1 hello -
bpx
őstag
válasz
BuktaSzaki
#4419
üzenetére
Tipikus probléma, hogy a JDBC driveren keresztül nem működik a futó query megszakítása.
Azt most ne kérdezd, hogy melyik verzió és milyen csillagállásnál gond, mert nem tudom, régi verziónál szokott baj lenni vele. SQL Developerben is akkor működik megbízhatóan, ha JDBC helyett Oracle kliens van használatban. -
bpx
őstag
válasz
Apollo17hu
#4342
üzenetére
Ha az XE helyett felraksz egy EE-t, akkor lesz lehetőséged olyan hagyományos típusú adatbázist létrehozni, amit mindenki más is használ, és amivel a felesleges szívástól megkíméled magad. Kivéve, ha a CDB/PDB világ érdekel.
Az XE-nek saját kísérletezős vagy development környezetben nem látom értelmét. Erre az EE is letölthető és használható licenc nélkül, és abban legalább nincsenek korlátozások.
-
bpx
őstag
válasz
Apollo17hu
#4340
üzenetére
Na nem, annyira tudtam már tegnap, amikor olvastam az XE-t, hogy ez lesz.
Az Oracle a 12.1-től (6 éve) bevezette a container database architektúrát, de senki nem használja, mert extra licenc költsége van, de nincs akkora hozzáadott értéke, hogy megérje.
Ehhez képest az Oracle, amit csinál az XE-vel meg a Developer VM-ekkel, az az öntökönrúgás kategória, erőlteti a container database-t, miközben ha egy kezdő bármilyen problémára rákeres neten, még mindig a nem container database-es megoldásokat látja, vagy gányolást.
Nem, te a root conatinerbe léptél be, és common usert próbáltál létrehozni (ehhez kell a C## prefix), erre nem az a megoldás, hogy lefuttattod az 'alter session set "_oracle_script"=true;' és úgy hozod létre a usert, csak sajnos az itt kapott hibára ez a Google első találat. Meg ugye rögtön DBA role csak a belépéshez, hogyne.
Pl. egy SQL Server-es analógiával élve: a masterdb-be gányoltál bele és oda készülsz betölteni user adatokat.
Csak az SQL Servernél már régóta van masterdb és mellette más adatbázisok, mindenki tudja mit hova tegyen (remélem), az Oracle-nél meg még csak most terjed ez az architektúra.
Nem, ilyet nem csinálunk, eleve rossz helyre csatlakoztál. Neked nem a root containerhez kell csatlakozni (service = xe), hanem az automatikuson létrehozott pluggable database-hez (service = xepdb1), és azon belül kell dolgozod. Persze ezt még a Oracle a saját doksijában sem írja le normálisan, ott is a root containerhez való csatlakozást mutatja példának.
Ez nem a te hibád, egy kezdő ezeket nem tudja, de a doksi nem jó, a Google meg a régi módszereket adja megoldásnak.Ha Oracle adatbázissal akarsz foglalkozni, akkor mondom, hogy mit ajánlok.
Elfelejted az XE-t, az Enterprise Edition is letölthető, arra ingyen használható, hogy otthon egyedül tanulj rajta (és az XE is egy több GB-os monstrum).
Magamnak a host OS-re sem telepíteném (meg Windowsra sem). VirtualBox, abba egy Oracle Linux, és arra mehet a 19c EE telepítése.
Ehhez alapvető Linux, virtualizáció, networking ismeretek kellenek, ha ez hiányzik, akkor simán csak telepítsd fel a gépedre és használd ott.
Az adatbázis létrehozásánál pedig ne válassz container database-t, és ha nem akarod magad tovább szivatni, akkor General Purpose template-ből csinálsz adatbázist. Ilyet egy valós rendszeren nem csinálunk, de most pont jó lesz arra, hogy felrakjon minden szemetet, ami a sample schema-khoz kell. Ugyanitt még ne válassz ki semmilyen sample schema hozzáadást.
A sample schema-k teljes halmaza már nem jön az adatbázissal, azokat githubról lehet letölteni és utólag telepíteni. -
bpx
őstag
válasz
Apollo17hu
#4170
üzenetére
Persze, mert a hintet nem oda kell rakni, hanem közvetlenül a SELECT után.
WITH
t1 as (...),
t2 as (...),
...
t20 as (...)
SELECT /*+ no_merge (t1 t2 ... t20) */ ...
FROM
t1,
t2,
...,
t20,
() as tx
WHERE
tx.mezo = t1.mezo(+) AND
tx.mezo = t2.mezo(+) AND
...
tx.mezo = t20.mezo(+)Vagy bele az inline view-ba:
WITH
t1 as (SELECT /*+ NO_MERGE */ ...),
t2 as (SELECT /*+ NO_MERGE */ ...),
...Ha azt akarod, hogy gyűjtse ki tempbe az egyes CTE-ket, akkor meg MATERIALIZE hint, pl.:
WITH
t1 as (SELECT /*+ MATERIALIZE */ ...),
t2 as (SELECT /*+ MATERIALIZE */ ...),
...De ez még mindig csak találgatás, plant kellene nézni futásidejű statisztikával.
-
bpx
őstag
válasz
Apollo17hu
#4167
üzenetére
Mindenki keresi az univerzális silver bulletet, de ilyen nincs.
Ha pl. az szeretnéd, hogy az optimizer ne fejtse ki és alakítsa át ezeket, akkor használhatod a NO_MERGE és NO_UNNEST hinteket attól függően, hogy az allekérdezés az csak inline view vagy tényleg subquery.
-
bpx
őstag
válasz
dellfanboy
#4129
üzenetére
Ez nem SQL, hanem PHP probléma.
$tagid, $autoid helyett $megrendelo_id, $autok_id változókat használsz a query-hez, és nem a CURDATE()-tel van baja, hanem az üres változók miatt a "(, , CURDATE())"-tel.
-
bpx
őstag
válasz
bandi0000
#4032
üzenetére
Ennyi erővel az árat és a darabszámot is ki lehetne tenni külön táblába, mert lehetséges, hogy különböző termékeknek ugyanannyi az egységára és ugyanannyi darabot vásároltak belőle ugyanakkor.
Ezt pl. úgy szokták csinálni, hogy külön táblába kerül a vásárlás és annak a tételei, hogy milyen termékeket vettek. Pl.:
VÁSÁRLÁS(vásárlás_id, dátum+idő)
VÁSÁRLÁS_TÉTEL(vásárlás_tétel_id, vásárlás_id, termék_id, db, ár) -
bpx
őstag
Mert pl. lehet, hogy tiltva van. Ennek by default 1-et kellene visszadni global és session szinten is:
SELECT @@GLOBAL.foreign_key_checks, @@SESSION.foreign_key_checks;Ha viszont 0, akkor nem történik meg a foreign keyek ellenőrzése, és büntetlenül lehet azt megsértő adatokat bevinni.
-
bpx
őstag
válasz
Ablakos
#3946
üzenetére
Kb. 2,5 éve van ilyen, hogy Red Hat Developer license.
[link] Itt rányomsz a letöltésre, elkezdi letölteni az ISO-t, és továbbít egy olyan oldalra, ahol leírja, hogy hogyan telepítsd. Kb. annyi a lényeg, hogy telepíteni kell a "Developer Tools" add-ont, és ha ez megvan, a telepítés végén az RH account adatok megadása után automatikusan regisztrálja a gépet, lesz rá 1 éves licenc, lehet vele használni a RH repot, stb. 1 év után, ha lejárt, kell rá renew, szintén ingyenes [link]
Ha másért nem, nekem legalább azért jó volt, mert így legalább elérem access.redhat.com-on a Subscriber Exclusive Contentet, mert egyébként nincs semmilyen RH előfizetésünk céges szinten.
-
bpx
őstag
válasz
soldi3r
#3943
üzenetére
Szerintem otthonra, 1 felhasználós környezetbe, tanulási célra, tök felesleges az XE, amikor erre a célra az Enterprise Editiont is bárki letöltheti az Oracle publikus oldaláról, és nincsenek benne XE szintű korlátozások, és ugyanúgy egy darab RPM-ből telepíthető. Az EE .rpm 3,3 GB, az XE .rpm meg 2,5 GB, tehát hiába Express Edition, az is egy jó nagy monstrum.
OS-ből ha Linux, akkor Oracle Linux (ingyenes, csak a support fizetős), RHEL (van ingyen licenc 1 accounthoz 1 gépre), SLES (nem tudom, max 5%-ban fordul elő Oracle alatt, nagyon ritkán találkozom vele), preferencia ebben a sorrendben. Otthoni környezetben esetleg Windows (na arra nem is jött ki a legújabb XE).
A desktop Linux distro-t felejtsük el, működésre lehet bírni rajta, egy Fedora-n még könnyebben, de egy Ubuntu-n már nehezebben, de nem is ezzel érdemes foglalkozni, hanem a hasznos dolgokkal. Pl. egy Oracle Linux-on alapból megy minden a saját repo-ból és beránt minden függőséget, létrehozza a usert, beállítja a kernel paraméteretek, limiteket, stb.
Annyi még, hogy fejlesztői irányból érdekel és nem infra/DBA oldalról, akkor kb. letöltesz egy előre összerakott virtuális gépet és kész: [link]
-
bpx
őstag
válasz
user112
#3906
üzenetére
Lehet a MIN helyett SUM, de ebben az esetben nincs jelentősége, hogy melyik, mert csoportonként csak 1 sorban lesz érték, a GROUP BY miatt viszont muszáj valamilyen aggregate functiont használni.
Az összeget bele lehet rakni új oszlopként, simán csak pl.:
min(Aerteke) + min(Berteke) as osszegVagy akár:
select
kod,
min(Aerteke) as Aerteke,
min(Berteke) as Berteke,
sum(ertek) as osszeg
from
(
select
kod,
ertek,
case when tipus = 'A' then ertek end as Aerteke,
case when tipus = 'B' then ertek end as Berteke
from
tabla
) group by kod; -
bpx
őstag
válasz
user112
#3904
üzenetére
Erre szoktunk PIVOT-ot használni, de egy ilyen egyszerű esetben a "lábbal hajtós" megoldás is elfogadható, pl.:
select
kod,
min(Aerteke) as Aerteke,
min(Berteke) as Berteke
from
(
select
kod,
case when tipus = 'A' then ertek end as Aerteke,
case when tipus = 'B' then ertek end as Berteke
from
tabla
) group by kod; -
bpx
őstag
válasz
#74220800
#3894
üzenetére
Először azt kellene tisztázni, hogy milyen fajta SQL, mert Oracle adatbázisban nincs olyan, hogy INT(2). Olyan van, hogy INT, amit egyébként senki nem használ, vagy olyan, hogy NUMBER(2, 0). Ez megy (és akkor még a VARCHAR2 szóba sem jött):
CREATE TABLE ELSO
(MASODIK NUMBER(2, 0) NOT NULL,
HARMADIK VARCHAR(14),
NEGYEDIK VARCHAR(13),
CONSTRAINT OSZT_PK PRIMARY KEY (MASODIK)); -
bpx
őstag
válasz
GreenIT
#3800
üzenetére
Fogalmazzunk inkább úgy, hogy az Oracle csak sokkal több pénzért tudná ezt, amit már egyre több helyen nem akarnak megfizetni, jogosan.
Kíváncsi vagyok medig tarthatják még a mostani árazást és üzletpolitikájukat.
Az infrastuktúra még elfogadható, de a support és az általuk szállított alkalmazás színvonala ezért a pénzért gyalázatos. -
bpx
őstag
Most akkor PIVOT/UNPIVOT azért van kilőve, mert nem használható, vagy mert nem sikerült megoldani vele?
with data as
(
select * from t_test
unpivot (value for val in (val1, val2, val3, val4, val5))
)
select a, b, c from (select val, value, label from data)
pivot (min(value) for label in ('A' as a, 'B' as b, 'C' as c))
order by val; -
bpx
őstag
válasz
Iginotus
#3660
üzenetére
Az egy nem correlated subquery (magyarul még szebb: korrelált allekérdezés), ezért ami belül van, az egyszer lefut, és kívül mindenhova az ott kapott értéket használja. Lehet belőle correlated subquery-t csinálni valami értelmetlen feltétellel és akkor majd miden sorra újból kiértékelődik. Persze ez nem szép és kapásból odaírnám kommentbe, hogy ez miért van belegányolva. Vagy marad a ciklus, amit már első ránézésre is el lehet olvasni.
create table forge (row_id, code_neu) as select rownum, 0 from dual connect by level <= 10;
create table oe (orgeh_code) as select rownum from dual connect by level <= 4;
select * from forge;
ROW_ID CODE_NEU
---------- ----------
1 0
2 0
3 0
4 0
5 0
6 0
7 0
8 0
9 0
10 0
select * from oe;
ORGEH_CODE
----------
1
2
3
4
update forge set code_neu =
(
select orgeh_code from oe
----
where forge.row_id = forge.row_id
----
order by dbms_random.value fetch first 1 row only
)
where row_id between 1 and 9;
select * from forge;
ROW_ID CODE_NEU
---------- ----------
1 1
2 3
3 1
4 2
5 1
6 1
7 4
8 3
9 4
10 0 -
bpx
őstag
válasz
SunyaMacs
#3650
üzenetére
select
t.topic_id,
t.topic_name,
coalesce(p.post_time, t.topic_time)
from
topics t
left join
(
select
topic_id,
max(post_time) as post_time
from
posts
group by
topic_id
) p
on (t.topic_id = p.topic_id)
;Ha meg azt akarnám, hogy gyors is legyen, akkor +1 oszlop a topics-ba, pl. last_post_time, amit post írásakor karban kell tartani, és akkor nem kell join meg aggregáció.
-
bpx
őstag
Az első változatot irtani kell.
Nem az átalakítás a nagy munka, hanem az, hogy ha index van az oszlopon, akkor az tipikusan a tábla.dátum_mező-re van, és nem pedig a to_char(tábla.dátum_mező...)-re, így a lekérdezés nem tudja használni az indexet, teljes táblát olvas, lassú. Persze lehet function based indexet létrehozni a to_char(tábla.dátum_mező...)-re is, de erre az esetre nem ez a helyes megoldás.
Ezen kívül az ilyen átalakításoknál az optimizer számosságbecslései is pontatlanak lehetnek, hiszen dátum típusnál tudja, hogy pl. 2017-01-01 előtt a 2016-12-31 van, de ha ugyanezt stringként kell becsülni, akkor olyan értékek is lehetségesek, amelyek dátumnál nem, pl. 2017-00AAAAAA, 2016-999990000, stb.
-
bpx
őstag
select * from (
select * from (
select
pilota, sum(pont) over (partition by pilota) as sum_pont,
vegeredmeny,
row_number() over (partition by pilota order by vegeredmeny) rn
from futam) where rn <= 4
) pivot
(min(vegeredmeny) for rn in (1 as er1, 2 as er2, 3 as er3, 4 as er4))
order by sum_pont desc;De szerintem MySQL lesz a kérdés.
-
bpx
őstag
(#3447) sztanozs
Ez tök ugyanaz, mint az eredeti.
(#3448) tm5
Ez is. Erre írja át magától az adatbázis.
Nyilván egyszerűbbek, de a kérés pont az volt, hogy ne ezt csinálja.
-
bpx
őstag
válasz
Apollo17hu
#3445
üzenetére
Ha most tényleg az a cél, hogy a 2 subqueryt egymástól független megcsinálja 1-1 alkalommal, akkor kb. így:
SELECT /*+ use_hash(t1 t2) */ t1.mezo_1
,t1.mezo_2
FROM (SELECT /*+ no_merge no_push_pred */ t.id
,t.mezo_1
,t.mezo_2
FROM tabla_1 t
WHERE feltetel_1
AND feltetel_2
...
AND feltetel_n) t1
,(SELECT /*+ no_merge no_push_pred */ t.id
FROM tabla_2 t
WHERE feltetel_1
AND feltetel_2
...
AND feltetel_n) t2
WHERE t1.id = t2.id;A subquery itt úgy viselkedik mintha view lenne. A view-kat az adatbázis "kifejti" ha tudja, az eredeti példát szerintem simán átírja az adatbázis úgy, mintha nem is lennének subquery-k, csak a 2 táblára a join. Ez a view merging, ezt akadályozza meg a no_merge hint.
Ha a view-kon kívül is vannak egyéb feltételek, azt az adatbázis be tudja helyezni a view-n belülre. Pl. a "select * from view1 where column1='...'" lekérdezést végre lehet úgy hajtani, hogy előállítja a view1 teljes eredményhalmazát, majd a végén alkalmazza a column1 szűrést, de úgy is, hogy a column1 szűrést átírja úgy, mintha a view-n belül lenne. Ez nem csak egyszerű szűrésekre működik, hanem joinra is, tehát miután előállította a t1 tartalmát, az adatbázis a t2-be már beviszi a tabla_2.id = t1.id szűrést és felhasználja a t1-ből jövő id értékeket, ez a join predicate pushdown. Ezeket tiltja a no_push_pred.
A use_hash-t meg csak a biztonság kedvéért tettem oda, hogy mindkettő subquery-t csak 1-szer csinálja meg, és ne válasszon nested loops-t.
Aztán ezen kívül még lehetnek mindenféle más optimalizálások, amelyekre most nem gondoltam és további hintek kellenének.
De persze nem ezt tartom a jó megoldásnak.
-
bpx
őstag
válasz
Apollo17hu
#3442
üzenetére
Bocsánat, de ennyi információ birtokában én is csak ennyit tudok mondani: olyat, ami gyorsít rajta. Legalább egy plant mutass, de végrehajtási statisztikákkal még jobb lenne.
-
bpx
őstag
válasz
Ablakos
#3356
üzenetére
RANK helyett DENSE_RANK-ot kellene használni.
Magyarázat helyett itt a különbség a kettő között, így talán érthetőbb:
ADAT RANK DENSE_RANK
---- ---- ----------
A 1 1
A 1 1
A 1 1
B 4 2
B 4 2
C 6 3
C 6 3
D 8 4
D 8 4
D 8 4
E 11 5
E 11 5
F 13 6Ezen kívül a nev és szuletesi_ido oszlopokra is szükség van.
Ja látom az már megvolt.
-
bpx
őstag
válasz
htcwanted
#3336
üzenetére
Nagyon jó, már csak az adatbázis típusa kellene, mert pl. Oracle-ben ez egy sima matview és nem írunk sem MERGE-t, sem INSERT .. SELECT-et, mert azoknál hatékonyabb.
A szűrés nélküli, teljes táblára vonatkozó DELETE-et meg csak indokolt esetben használjuk, mert egyébként felesleges pazarlás. Simán TRUNCATE és kész.
-
bpx
őstag
válasz
DopeBob
#3157
üzenetére
Akkor viszont:
with st as
(
select 'K10' as text from dual union all
select 'K12' as text from dual union all
select 'K13' as text from dual union all
select 'K99' as text from dual
),
data as
(
select 1 as value from dual
)
select
data.value,
st.text
from
st,
data
order by
data.value,
st.text
;
VALUE TEXT
---------- ----
1 K10
1 K12
1 K13
1 K99 -
bpx
őstag
válasz
#30734848
#3142
üzenetére
Hát én egy regexpet ilyenkor meg nem írok már, de a sima SQL még belefér egy hosszú nap után:
create table t1 (text varchar2(20 char));
insert into t1 values ('123456123');
insert into t1 values ('12342');
insert into t1 values ('229898012342');
select text from t1;
TEXT
--------------------
123456123
12342
229898012342
select
text,
listagg(c, '') within group (order by c) as uniq_c
from
(
select
distinct text, substr(text, level, 1) as c
from
t1
connect by level <= length(text)
)
group by
text
;
TEXT UNIQ_C
-------------------- --------------------
12342 1234
123456123 123456
229898012342 0123489 -
bpx
őstag
Kell egy adatbázis job, ott van rá az adatbázis saját ütemezője. Mi a baj azzal?
DBMS_SCHEDULER helyett van DBMS_JOB is, de az a régi módszer, nem ajánlom, arról le kellene szokni.Vagy ha nagyon Windows jobot akarunk (inkább ne), akkor kb. ennyit kell beütemezni:
set ORACLE_HOME=...
set ORACLE_SID=...
set PATH=%ORACLE_HOME%\bin;%PATH%
sqlplus user/password @script.sql -
bpx
őstag
válasz
bambano
#3100
üzenetére
Azért, mert akkor született a döntés a napok kihagyásáról, és az Oracle meg fogta magát, és ezt vette alapul. Kipróbáltam, a területi beállításoknak erre nincs hatása, tehát én hiába állítom pl. UK-ra, attól még nem fogja az 1752-t 355 naposnak számolni, hanem ugyanúgy 1582-t mondja rövidebbnek.
-
bpx
őstag
válasz
lordring
#2979
üzenetére
Az SQL Server is tudja már 2008-tól az ehhez szükséges aggregációs kiegészítéseket. Kicsit eltördeltem, hogy látszon mit módosítottam:
SELECT
T0.[ItemCode], T0.[Dscription], T0.[Quantity], T0.[Price], T0.[Currency],
sum(T0.[LineTotal]), -- eredeti helyett sum, ez valojaban csak az utolso sorban lesz osszeg
sum(T0.[TotalFrgn]), -- eredeti helyett sum, ez valojaban csak az utolso sorban lesz osszeg
T2.[CardName], T0.[ShipDate], T1.[CardCode]
FROM
CSI1 T0 INNER JOIN OITM T1 ON T0.ItemCode = T1.ItemCode
INNER JOIN OCRD T2 ON T1.CardCode = T2.CardCode
WHERE
T0.[ShipDate] >=[%0]AND T0.[ShipDate] <=[%1] AND T2.CardName = '[%3]'
-- es itt jon a lenyeg
GROUP BY
GROUPING SETS((),(T0.[ItemCode], T0.[Dscription], T0.[Quantity], T0.[Price], T0.[Currency], T2.[CardName], T0.[ShipDate], T1.[CardCode] )); -
bpx
őstag
Mivel nem írtál adatbáziskezelőt, automatikusan feltételezem, hogy szabad a pálya és lehet analitikus függvényeket használni (Oracle).
select
b.id, b.name, a.value, a.timestamp
from
b
join
(
select
id, value, timestamp
from
(
select
id, value, timestamp,
rank() over (partition by id order by timestamp desc) as rn
from
a
)
where
rn = 1
) a on (b.id = a.id); -
bpx
őstag
Egy megoldás már le lett írva, így csak a hibára reagálnék. Azért nem ad eredményt, mert pl. annak, hogy WHERE ROWNUM = 2, nincs értelme, soha nem fog eredményt adni. A ROWNUM eredményhalmazra vonatkozik, és nem táblára. A ROWNUM értéke folyamatosan növekszik az eredményhalmaz sorainak számával együtt. A ROWNUM = 1 azért működik, mert az első sorra teljesül, hogy az az első sor. A ROWNUM = 2 azért nem ad eredményt, mert az első sorra nem teljesül, hogy az a második sor, így nem kerül be az eredményhalmazba, és a ROWNUM értéke sem fog növekedni, így nem lesz eredmény sem.
Na, lassú voltam.
-
bpx
őstag
válasz
dellfanboy
#2641
üzenetére
pl. február:
where
date_to is null
and trunc(date_from, 'MM') = date'2014-02-01' -
bpx
őstag
válasz
supercharley
#2637
üzenetére
akkor itt a buta verzió:
select a1.datum, a1.azonosito, (select sum(a2.darab) from adattabla a2 where a2.azonosito = a1.azonosito and a2.datum <= a1.datum) from adattabla a1
order by a1.datum, a1.azonosito; -
bpx
őstag
válasz
supercharley
#2634
üzenetére
select datum, azonosito, sum(darab) over (partition by azonosito order by datum, azonosito range between unbounded preceding and current row) from adattabla
order by datum, azonosito; -
bpx
őstag
válasz
dellfanboy
#2633
üzenetére
where
extract(day from date_from) = 1
and extract(day from date_to + 1) = 1
and trunc(date_from, 'MM') = trunc(date_to, 'MM') -
bpx
őstag
válasz
bambano
#2610
üzenetére
Nem tettem tönkre, ezt egyszerűen így kell leírni, mert sajnos nincs LIMIT. A WHERE előbb van, mint az ORDER BY, a másodikban levő subquery azt jelenti, hogy "olvass fel <4 sort a táblából és rendezd", és nem pedig azt, hogy "kérem rendezés után az első <4 sort".
ez csak abban az egy esetben lehet ugyanolyan eredményű, ha az oracle képes olyan mélyen értelmezni a lekérdezést, hogy a külsö selectben használt where rownum<4 klauzát képes bevinni a belső selectbe.
Hasonló, de a sorok számára vonatkozó feltételeket speciálisan kezeli, ezek a végrehajtási tervben megjelenő STOPKEY műveletek, amelyek csak addig futtatják a gyerekeiket, amíg el nem érik a megadott limitet. Tehát valóban az történik, hogy úgy kezd neki, mintha az egészet fel kellene olvasni, de 3 sornál megáll. Az adatbázis az egyéb feltételeket is simán mozgatja szintek között, ha szerinte úgy hatékonyabb, azokra nincs külön művelet.
A subquery-t ha lefuttatom magában, nyilván végigmegy 1 millió sorra, hiszen nem lesz ott a külső szűrés, ami leállítja 3 sornál.
-
bpx
őstag
válasz
bambano
#2608
üzenetére
OK, akkor kiegészíteném annyival, hogy Oracle-ben nincs különbség.
SELECT /*+ GATHER_PLAN_STATISTICS */ t.aru_nev, t.aru_egysegar FROM
(SELECT aru_nev,aru_egysegar, rank() OVER (ORDER BY aru_egysegar DESC)
AS sorrend FROM aruk) t WHERE t.sorrend < 4 ORDER BY t.aru_egysegar
Plan hash value: 68470586
-----------------------------------------------------------------------------------------------------
| Id | Operation | Name | Starts | E-Rows | A-Rows | A-Time | Buffers |
-----------------------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | | 3 |00:00:00.01 | 4 |
| 1 | SORT ORDER BY | | 1 | 1000K| 3 |00:00:00.01 | 4 |
|* 2 | VIEW | | 1 | 1000K| 3 |00:00:00.01 | 4 |
|* 3 | WINDOW NOSORT STOPKEY | | 1 | 1000K| 4 |00:00:00.01 | 4 |
| 4 | TABLE ACCESS BY INDEX ROWID| ARUK | 1 | 1000K| 5 |00:00:00.01 | 4 |
| 5 | INDEX FULL SCAN DESCENDING| I_ARU_AR | 1 | 1000K| 5 |00:00:00.01 | 3 |
-----------------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
2 - filter("T"."SORREND"<4)
3 - filter(RANK() OVER ( ORDER BY INTERNAL_FUNCTION("ARU_EGYSEGAR") DESC )<4)Az első query-t egy az egyben másoltam, a másodiknál a limitet át kellett írnom, mert az itt nincs.
SELECT /*+ GATHER_PLAN_STATISTICS */ * FROM (SELECT
aru_nev,aru_egysegar FROM aruk ORDER BY aru_egysegar DESC) aruk_kivonat
where rownum < 4 ORDER BY aruk_kivonat.aru_egysegar ASC
Plan hash value: 2883829479
-----------------------------------------------------------------------------------------------------
| Id | Operation | Name | Starts | E-Rows | A-Rows | A-Time | Buffers |
-----------------------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | | 3 |00:00:00.01 | 4 |
| 1 | SORT ORDER BY | | 1 | 3 | 3 |00:00:00.01 | 4 |
|* 2 | COUNT STOPKEY | | 1 | | 3 |00:00:00.01 | 4 |
| 3 | VIEW | | 1 | 3 | 3 |00:00:00.01 | 4 |
| 4 | TABLE ACCESS BY INDEX ROWID| ARUK | 1 | 1000K| 3 |00:00:00.01 | 4 |
| 5 | INDEX FULL SCAN DESCENDING| I_ARU_AR | 1 | 3 | 3 |00:00:00.01 | 3 |
-----------------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
2 - filter(ROWNUM<4)0,01 másodperc, 4 darab blokk érintésével megoldotta mindkettő. Egyedüli látványos különbség, hogy az elsőnél mindenhol 1000K a becsült sorok száma.
A 2 query egyébként nem ekvivalens, rank() helyett row_number()-rel lenne az.
-
bpx
őstag
válasz
bambano
#2605
üzenetére
Window function használatával sem fog a 20 millió rekordon végigmenni, ugyanúgy ki tudja választani index mentén az első 3 darabot, és egy ilyen egyszerű példában nincs különbség.
Ugyanakkor én inkább használnám az egyszerűbb módszert. A window function akkor lenne hasznos igazán, ha lenne PARTITION BY, de nincs. Ezen kívül a becsült kardinalitás a window functionnel sokkal pontatlanabb, így sokkal nagyobb az esély egy kevésbé hatékony végrehajtási tervre.
-
bpx
őstag
válasz
DopeBob
#2511
üzenetére
MySQL-es példát mutatsz, de CONNECT BY-t szeretnél használni, ami az "igazi" Oracle-ben van, MySQL-ben nincs, így maradjunk az Oracle-nél. A példádat kicsit kiegészítettem, mert ha csak két szintes a hierarchia, akkor túl triviális, még CONNECT BY sem kell.
create table table1 (id varchar2(10), part varchar2(100), qty int);
insert into table1 (id, part, qty) values ('1', '1--1', 2);
insert into table1 (id, part, qty) values ('1', '1--2', 4);
insert into table1 (id, part, qty) values ('1', '1--3', 8);
insert into table1 (id, part, qty) values ('1', '1--4', 5);
insert into table1 (id, part, qty) values ('1--1', '1--1--1', 2);
insert into table1 (id, part, qty) values ('1--1', '1--1--2', 2);
insert into table1 (id, part, qty) values ('1--1', '1--1--3', 2);
insert into table1 (id, part, qty) values ('1--2', '1--2--1', 2);
insert into table1 (id, part, qty) values ('1--3', '1--3--1', 2);
insert into table1 (id, part, qty) values ('1--4', '1--4--1', 3);
insert into table1 (id, part, qty) values ('1--4--1', '1--4--1--1', 7);
commit;Lekérdezés + eredmény:
select id, part, qty,
(select exp(sum(ln(t2.qty)))
from table1 t2
start with t2.id = t1.id and t2.part = t1.part
connect by prior id = part
) mqty
from table1 t1
start with id = '1'
connect by id = prior part;
ID PART QTY MQTY
---------- -------------------- ---------- ----------
1 1--1 2 2
1--1 1--1--1 2 4
1--1 1--1--2 2 4
1--1 1--1--3 2 4
1 1--2 4 4
1--2 1--2--1 2 8
1 1--3 8 8
1--3 1--3--1 2 16
1 1--4 5 5
1--4 1--4--1 3 15
1--4--1 1--4--1--1 7 105Ha csak azok érdekelnek, amelyek a hierarchia utolsó szintjén vannak:
select id, part, qty, mqty from (
select id, part, qty,
(select exp(sum(ln(t2.qty)))
from table1 t2
start with t2.id = t1.id and t2.part = t1.part
connect by prior id = part
) mqty,
connect_by_isleaf leaf
from table1 t1
start with id = '1'
connect by id = prior part)
where leaf = 1;
ID PART QTY MQTY
---------- -------------------- ---------- ----------
1--1 1--1--1 2 4
1--1 1--1--2 2 4
1--1 1--1--3 2 4
1--2 1--2--1 2 8
1--3 1--3--1 2 16
1--4--1 1--4--1--1 7 105 -
bpx
őstag
válasz
dellfanboy
#2382
üzenetére
na tehát akkor:
user_tables = saját tábláid
all_tables = olyan táblák, amelyek az aktuális felhasználó számára elérhetőek (amelyek lehetnek sajátjai, vagy másé)
dba_tables = összes tábla az adatbázisbanaz utolsót viszont csak akkor tudod lekérdezni, ha kapsz megfelelő jogosultságot
-
bpx
őstag
válasz
PumpkinSeed
#2378
üzenetére
all_tables
a user_tables csak a saját táblákat mutatja -
bpx
őstag
válasz
dellfanboy
#2336
üzenetére
amikor futtatsz egy lekérdezést, ahhoz az adatbázis végrehajtási tervet készít, és az optimizer az összes lehetséges tervet megvizsgálja, és azokból választja ki a szerinte optimálisat
ha mondjuk így néz ki az sql (Oracle), hogy:select /*+ ordered use_hash(tabla1 tabla2) */ oszlop1, oszlop2, ... from tabla1, tabla2, tabla3 ...
akkor a /*+ ... */ közti "kommentek" valójában optimizer hintek, amivel befolyásolhatod hogy milyen terv készüljön
az ordered azt jelenti, hogy a tábláknál a join sorrendje az lesz, ahogy le van írva az sql szövegében, és nem az adatbázis dönti el, tehát a fenti példában először veszi a tabla1-et, utána a tabla2-t, majd a tabla3-at
a use_hash meg azt jelenti, hogy a tabla1-nél es tabla2-nél hash joint fog használni (míg a hint nélkül lehet, hogy nested loops join vagy merge join lenne)azt meg, hogy miért jó a fromba beágyazott select, nem tudom

sokszor meg lehet oldani anélkül is, ha viszont kell, akkor meg van sokkal olvashatóbb módszer is: with .. as ..
pl. (persze itt pont nem kell, meg az egyszerűsége miatt nincs is nagy különbség, de most ennyire telik tőlem):select * from ( select * from hr.employees where hire_date > date '2005-01-01') e2005
where e2005.salary > 15000;
with e2005 as (select * from hr.employees where hire_date > date '2005-01-01')
select * from e2005 where e2005.salary > 15000; -
bpx
őstag
válasz
dellfanboy
#2333
üzenetére
where oszlop between to_date('2014-01-01', 'YYYY-MM-DD') and to_date('2014-02-01', 'YYYY-MM-DD')
-
bpx
őstag
válasz
PumpkinSeed
#2286
üzenetére
Azért, mert alapértelmezett esetben a TO_CHAR dátum bemenet esetén a lehetséges leghosszabb kimenetre készülve rak paddinget (extra space-ek), ezért amikor a te 'THURSDAY'-t vársz, ott valójában 'THURSDAY '-t kapsz, mert a 'WEDNESDAY' a leghosszabb, és minden napot 9 karakterre egészít ki emiatt.
Ha ezt nem szeretnéd, akkor a 'DAY' helyett használj 'FMDAY'-t, amiben az FM kikapcsolja a paddinget.
Ezen kívül:
- az UPPER felesleges, mert a 'DAY' miatt eleve nagybetűsen kapod az eredmény ('day' - kisbetű)
- ha a TO_CHAR-t a megfelelő NLS paraméterrel kiegészíted, akkor rögtön magyarul kapod a napot
- az INITCAP függvénnyel lehet a szavak kezdőbetűjét nagybetűre cserélni, ha ez az igényPl:
SQL> SELECT INITCAP(TO_CHAR(TO_DATE('1994-01-06','YYYY-MM-DD'),'FMDAY', 'NLS_DATE_LANGUAGE = HUNGARIAN')) AS VALAMI FROM DUAL;
VALAMI
------------
Csütörtök -
bpx
őstag
válasz
PumpkinSeed
#2281
üzenetére
első találat
-
bpx
őstag
válasz
PumpkinSeed
#2237
üzenetére
Az, hogy odamásolsz pl. egy CSV file-t és tudsz belőle úgy lekérdezni, mintha közönséges tábla lenne.
-
bpx
őstag
válasz
Apollo17hu
#2199
üzenetére
igy esetleg? ugy emlekszem lehet ilyet
AND NVL(t1.calendar_date, to_date('20131231', 'yyyymmdd')) = to_date('20131231', 'yyyymmdd')
AND NVL(t2.calendar_date, to_date('20131231', 'yyyymmdd')) = to_date('20131231', 'yyyymmdd') -
bpx
őstag
válasz
kenesei1982
#2148
üzenetére
most akkor MySQL vagy MSSQL support kell?
-
bpx
őstag
pont az amit ir a hiba
csak classid szerint megy a group by, ilyenkor a tobbi oszlopra "osszesito" fuggveny kell, pl. COUNT, MAX, vagy azokra is group by-olni kell
az a baj a lekerdezessel, hogy mivel a classification oszlopra egyik sincs, igy annak erteke nem determinisztikus
mysql sajnos megenged ilyen lekerdezest, mas adatbaziskezelok szerencsere nem -
bpx
őstag
válasz
csabyka666
#2124
üzenetére
Van ugye a "where lower(oszlop) like '%alma%'" modszer, de ha valami okosabb kell, akkor vannak erre RDBMS-specifikus eszkozok, pl. [link]
-
bpx
őstag
válasz
dellfanboy
#2012
üzenetére
create database link B connect to user identified by pw using 'A';
select * from tabla@B; -
bpx
őstag
na ezt például kifejezetten nem szeretem a mysql-ben, hogy egyáltalán engedi a group by-t így használni...
(a másik amit utálok, ha nincsenek kiírva az aliasok mindenhol
)
egyébként nem csak a vehiclename-mel van gond ha megnézed, hanem a minutes, seconds, milliseconds sem jóSELECT
d.Name,
t.Minutes, t.Seconds, (t.Milliseconds/1000) AS Milliseconds,
x.besttime AS besttime,
r.TrackTitle,
v.VehicleName
From
tracking t,
driver d,
tracks r,
vehicle v,
(select a.driverid, min((a.Minutes*60)+(a.Seconds)+(a.Milliseconds/1000)) as besttime from tracking a group by a.driverid) x
WHERE
d.id = t.driverid
AND t.driverid = x.driverid
AND t.trackid = '1'
AND t.trackid = r.id
AND t.vehicleid = v.id
AND (t.Minutes*60)+(t.Seconds)+(t.Milliseconds/1000) = x.besttime
order by x.besttime; -
bpx
őstag
válasz
dellfanboy
#1900
üzenetére
"select *from tábla_xxxxxx"
igen, rosszul irtad
@ kell _ helyettselect *from tábla@aaaaaa
+ a dblink neve aaaaaa, mivel az xxxxxx az a TNS nev a mintad alapjan
-
bpx
őstag
válasz
Speeedfire
#1887
üzenetére
"Subqueries cannot be used in the FROM clause of a view. "
-
bpx
őstag
igen, es ez az, ami nincs sajnos
ami van, ahhoz kell korites, es tudni kell, mit fog visszaadni a query
ugyanez van Oracle-ben is, EXECUTE IMMEDIATE-tel kb. akarmit vegre lehet hajtani, de csak PL/SQL-ben, es ha van kimenete, ahhoz bizony programozni kell, hogy lassak belole valamit
ha meg elore nem ismert a kimenet strukturaja, hat hagyjuk...
az sp_executesql ahogy nezem, az is ugyanilyennem tudom mekkora az adathalmaz, es hogy kritikus folyamat, vagy eleg az "egyszer fusson le es kesz", de erre a legegyszerubb modszer szerintem mindenfele eval kinlodas nelkul, hogy nem az adatbazisban rakom ossze a query-t dinamikusan es futtatok mindent, hanem a kliens (pl. egy shell script) elkeri a futtatando query-ket es szepen beadagolja
pl. van egy script, ami lekeri a queryket, es futtatja oket psql-el, a kimenetet meg kitolja mondjuk CSV fajlba (vagy amibe kell)
vegen meg a fajlokra mehet a grafikon generatornem tul szep, de legalabb egyszeru
-
bpx
őstag
na, jó hogy kérdezed, mert nem hibátlan
a +5 -2 az működik a többi napon is (kivéve 1-et)
azért pont ennyi, mert a hét első napja a DAYOFWEEK szerint az vasárnap, és korrigálni kella vasárnappal viszont pont emiatt gond van...
de most rátaláltam a csodás WEEKDAY() függvényre, aminél nem kell korrigálni, és a hét minden napján jó:
select date(date_sub(now(), INTERVAL WEEKDAY(now())+7 DAY)), date(date_sub(now(), INTERVAL WEEKDAY(now()) DAY));
-
bpx
őstag
mysql rejtelmeit nem igazán ismerem, de ennyit sikerült összehozni

mysql> select date(date_sub(now(), INTERVAL DAYOFWEEK(now())+5 DAY)), date(date_sub(now(), INTERVAL DAYOFWEEK(now())-2 DAY));
+---------------------------------------------------------+---------------------------------------------------------+
| date(date_sub(now(), INTERVAL DAYOFWEEK(now())+5 DAY)) | date(date_sub(now(), INTERVAL DAYOFWEEK(now())-2 DAY)) |
+---------------------------------------------------------+---------------------------------------------------------+
| 2013-04-15 | 2013-04-22 |
+---------------------------------------------------------+---------------------------------------------------------+"WHERE mezo1 > X-1. hét első napja AND mezo2 < X-1. hét utolsó napja."
nem a teljes hét kell?
mezo1 >= X-1. hét első napja AND mezo1 < X. hét első napja -
bpx
őstag
válasz
Flashback
#1706
üzenetére
ilyenkor az a helyzet, hogy ez adatbaziskezelonkent valtozik es nem tudhatjuk mire gondoltal, ezert irtam egy olyat, ami hozzam a legkozelebb all

de egyebkent MS SQL-ben is van [link]
ha regebbi verzio, akkor a ROUND-ot is lehet hasznalni [link]
a harmadik parametere ha nem 0, akkor nem kerekit, hanem siman csak levagja
Új hozzászólás Aktív témák
- Epic Store Ünnepi Ajándékozás - 7. nap: The Callisto Protocol
- D1Rect: Nagy "hülyétkapokazapróktól" topik
- Horgász topik
- És akkor a memóriapánik után beköszöntött a HDD-pánik
- Kuponkunyeráló
- Yettel topik
- The Division 2 (PC, XO, PS4)
- Apple MacBook
- Xiaomi 15T - reakció nélkül nincs egyensúly
- Világ Ninjái és Kódfejtői, egyesüljetek!
- További aktív témák...
- LG 32GP850-B 32'' Sík QHD 165 Hz 16:9 G-Sync/FreeSync NanoIPS Gamer Monitor - Karácsonyi akcióban!
- RYZEN 7 5800X + hűtött VRM-es A520 alaplap + 32GB hűtőbordás DDR4 kit! GAR/SZÁMLA (a Te nevedre)!
- Noblechairs Epic - Valódi bőr
- iPhone 15 PLUS 128GB kék sérült kijelző, KÁRTYAFÜGGETLEN! Akkumlátor 90%! Fulldoboz!
- GAMER PC - i7-7700, 16GB DDR4, GTX 1650
- HIBÁTLAN iPhone 15 Pro 256GB Black Titanium -1 ÉV GARANCIA - Kártyafüggetlen, MS3503
- GYÖNYÖRŰ iPhone 12 mini 128GB Blue -1 ÉV GARANCIA - Kártyafüggetlen, MS3854,94% Akkumulátor
- iPhone 13 Pro Max 128GB 100% (1 év Garancia)
- Apple iPad 10th Wi-Fi + Cellular - Silver - 64GB - BONTATLAN - ÚJ
- 186 - Lenovo Legion 5 (15IRX10) - Intel Core i7-13650HX, RTX 5070
Állásajánlatok
Cég: Laptopszaki Kft.
Város: Budapest
Cég: BroadBit Hungary Kft.
Város: Budakeszi




