Hitrost računalnika in “virtualne živalice”

Današnji prispevek nima hude uporabne vrednosti, ponuja pa zanimiv pogled na moč današnjih računalnikov.

V zadnji številki reviji ŽIT (Življenje in tehnika) je tudi članek o evolucijskih algoritmih. Ker se s to vedo računalništva nisem ukvarjal vse od programiranja prvih preprostih programov in posledično tki. ‘Igre življenja’, sem članek z veseljem prebral.

Čisto tako vmes: ‘Igra življenja’ je zelo preprost računalniški algoritem, kjer je svet predstavljen kot 2D mreža. V vsakem polju na mreži lahko »živi« organizem. V kolikor je ob njem še en organizem, potem naslednjo generacijo preživita oba in mogoče ustvarita novega potomca, če ob njem ni nobenega organizma potem pogine zaradi osamljenosti, če je ob njem preveč organizmov pogine zaradi prenaseljenosti… V glavnem, kot programer imate na voljo različne pogoje in s tem nadzorujete kako »vaš svet« živi.

Če se torej povrnem k tematiki. Ko sem prebral članek, ki je sicer resnici na ljubo čisto prekratek in ne pove kaj veliko, me je prešinilo vprašanje: “Kako hitro pa lahko kaj dandanes simuliramo življenje v računalniku?”.

V svetu evolucije ima mati narava pač na voljo generacije živih biti, da se »izživlja« nad njimi in nad nekaterimi lahko to hitro počne (recimo vinske mušice imajo zelo kratko življenjsko dobo in zato lahko ima vsak dan novo generacijo). Po drugi strani pa ljudje potrebujemo kar 20 let za novo generacijo (no dandanes se to pomika proti 30 let). Kako hitro pa lahko dandanašnji računalnik torej simulira življenje oz. posamezne generacije?

Seveda je to čisto presplošno vprašanje in odgovora nanj niti ne gre iskati, saj je predvsem pomembno koliko dela mora opraviti nek algoritem da ustvari novo generacijo. To vprašanje je torej presplošno, je pa zanimivo kako hitri pa so današnji računalniki v primerjavi z nečim, kar je nam blizu oz. s čimer se lahko poistovetimo.

V našem svetu je nekako 1 sekunda minimalni čas neke akcije. Predpostavimo torej da sestavljamo kocke in vsako sekundo smo sposobni zložiti dve kocki. Sedaj pa si predstavljajo računalnik, ki ravno tako opravlja neke naloge in v neki enoti je sposoben opraviti minimalno delo. Kakšna je torej tista minimalna enota v kateri je računalnik sposoben opraviti neko delo?

V računalniku je glavno božanstvo »ura«, ki udarja in vsak udarec ure (CPU cikel), računalnik izvede eno operacijo. (Seveda to spet ni čisto res, saj je dandanašnji računalnik sposoben v enem ciklu narediti celo več kot 1 operacijo a pustimo takšne »malenkosti« in se osredotočimo na zanimivosti). Hitrost računalnika pa merimo ravno v hitrosti njegove ure in hitrejša kot je ura hitrejši je računalnik (spet ne bodimo dlakocepski!).

No in sedaj si končno poglejmo kako hitro tiktaka nek čisto povprečen računalnik. V času pisanja tega prispevka lahko za 200EUR kupimo namizni računalnik, ki tiktaka s hitrostjo 3,6GH. Torej 3,g »gigahercov« ali 3.600.000.000 cikov na sekundo! Računalnik za 200EUR torej v eni sekundi opravi vsaj 3600 milijonov operacij.

Seveda pa računalnik ne more oz. vsaj ni smiselno da dela kar nekaj brezveze zato mora navodila, kaj naj počne, dobivati iz svoje okolice. Predstavljamo si, da je računalnik človek, ki sedi za mizo in opravlja pisarniško delo, ki je zapisano na listih, listi pa se nahajajo na njegovi mizi, v predalih mize, v omarah v sobi, v drugih sobah, v drugih hišah, v drugih mestih…. Na drugih planetih.

Računalniku najbližje so njegovi registri, ki jih ni ravno veliko (nekaj 10) in od njih dobi nov list v enem samem ciklu – to je torej enakovredno listu na mizi. Naslednje področje, ki mu lahko dostavi list je tki. L1 predpomnilnik. Do njega potrebuje 4 cikle in to bi predstavljalo predal ob mizi. Potem je L2 predpomnilnik do katerega potrebuje 10 ciklov, pa L3 predpomnilnik, do katerega potrebuje 70 ciklov in šele potem pride tisto, ker vsi poznate – to je glavni pomnilnik računalnika (famozni RAM) in za dostop do njega potrebuje računalnik nekaj 100 ciklov.

Da bi se ni izgubljali v besedilu si poglejmo kar tabelo z dostopi. Seveda so vsi podatki v tabeli približni (za vse »ne-fizike« še hitra ponovitev časovnih enot: 1s = 1.000 ms (milisekund) == 1.000.000 mikrosekund = 1.000.000.000 ns (nanosekund))

Dostop Št. cikov Porabljen čas
Register 1 0,3ns
L1 predpom. 4 1,2ns
L2 predpom. 10 3ns
L3 predpom. 70 21ns
RAM 400 120ns
SSD disk 400.000 120.000ns
»navaden« disk 15.000.000 4,5ms

Ok. S to tabelo smo izčrpali vse, ki računalniku lahko dajejo ukaze in se nahajajo v njegovi škatli. Ob tem pa smo uvideli tudi, da je razmišljanje v ciklih utrujajoče, zato se preusmerimo samo na čas in si poglejmo dostop do drugih računalnikov in interneta

Dostop Porabljen čas
Register 0,3ns
L1 predpom. 1,2ns
L2 predpom. 3ns
L3 predpom. 21ns
RAM 120ns
SSD disk 120.000ns
»navaden« disk 4,5ms
mrežni disk 10ms
Strežnik SIOL 20ms
Strežnik v Ameriki 200ms

In sedaj je čas, da vam predstavim glavno tabelo, ki me je tudi vodila v zapis tega prispevka. Povrnimo se torej na analogijo živih bitij, ki bi živela virtualno življenje v vašem računalniku. In privzamimo, da je en cikel v računalniku pač 1 sekunda njihovega življenja.

Dostop Računalnik Virtualno bitje
Register 0,3ns 1s
L1 predpom. 1,2ns 4s
L2 predpom. 3ns 10s
L3 predpom. 21ns 1min
RAM 120ns 7min
SSD disk 120.000ns 4,5dni
»navaden« disk 4,5ms 173dni
Mrežni disk 10ms 1 leto
Strežnik SIOL 20ms 2leti
Strežnik v Ameriki 200ms 20let

Naše virtualno bitjece mora torej kar 20let čakati, da dobi podatek iz strežnika v Ameriki 🙂

Kaj sem vam sploh želel prikazati s to analogijo? Ne vem sicer ali mi je uspelo, a želel sem vam prikazati, kako smo ljudje povsem nesposobni dojemati razmerje količin kadar so slednje nepredstavljivo majhne ali nepredstavljivo velike. S stališča računalnika je dostop do registra in dostop do strežnika v Ameriki sorazmerno kot 1 sekundna proti 20 letom!

Virtualna bitja torej živijo zelooo hitro. Mogoče še ena zelo zanimiva primerjava.

Moj delovni računalnik se prestarta v 15 sekundah. Če torej virtualno bitje, ki živi v mojem računalniku in katerega ena sekunda življenja predstavlja 1 cikel mojega računalnika (ki je mimogrede, samohvala!, še hitrejši od prej predstavljenega) uspavamo, ko se računalnik ugasne; koliko čase preteče, ko se računalnik spet zbudi?

Analogija je torej sledeča. Ko se računalnik ugasne se podatki o virtualnih bitjih shranijo na disk in ko se računalnik prižge, se podatki o virtualnih bitjih zopet preberejo ter bitja zopet oživijo. Kot, da bi nas uspavali in potem bi z vesoljsko ladjo potovali daleč vstran, nakar bi nas zopet prebudili. Kot rečeno, traja zagon mojega računalnika 15 sekund, kar je torej 15.000.000.000 ns oz. 45.000.000.000 sekund v življenju virtualnega bitja oz. 1400 let!

Za virtualna bitja mojega računalnika traja torej ponovni zagon računalnika 1400 let. Zanimivo!

Spet DropBox

Že skoraj tri leta je minilo odkar sem opisal, tedaj še ne tako zelo znano, spletno storitev Dropbox. Ker je prispevek še vedno popularen (glede na statistko obiska) vam bom danes pokazal še kako iz, že teko zelo dobre storitve, mogoče iztisniti še več.

Ko si torej začnete uporabljati DropBox, slej ali prej želite kakšno sliko, datoteko, film… deliti tudi s kom drugim. Tedaj v DropBox-u izberete opcijo ‘Copy public link’ in storitev vam pove preko katere javne povezave bodo lahko tudi drugi uporabniki prišli do vaše datoteke.

V mojem primeru sem na splet dal sliko konja in v kolikor zahtevam povezavo, mi DropBox vrne tole: https://www.dropbox.com/s/oxg08i5gz04wnxp/horse.jpg?dl=0. Kot vidite je to navadna spletna povezava in če kliknete nanjo boste v brkljalnik naložili sliko konja.

Obstaja pa še ena opcija in sicer, da na konec povezave dodate ?dl=1, v tem primeru brkljalnik ne bo poskušal odpreti datoteke, temveč jo bo uporabniku vedno kar naložil (“dovnlovdal”; kot temu pravimo dandanes)

https://www.dropbox.com/s/oxg08i5gz04wnxp/horse.jpg?dl=1

 

Avtomatično številčenje v Word-u (III. del)

V prvem in drugem delu sem pokazal kako v Wordu deluje avtomatično številčenje, v zadnjem blogu te serije, pa bom pokazal kako številčiti poljubne elemente in seveda kako v Word-u številčiti slike kot 10a, 10b.

Poljubno številčenje

Za uporabo avtomatičnega številčenja nam ni potrebno poseči po bolj ali manj skritih oknih Worda, temveč lahko polje preprosto vstavimo sami. Ko želimo nek element oštevilčiti se postavimo na trak Vstavljanje in iz opcije Hitri deli izberemo Polje…

Odpre so novo okno za vstavljanje polj:word_stevilcenje6
V oknu poiščemo polje SEQ, mu zgoraj dodamo poljubno oznako (npr. člen) in že imamo novo avtomatično številčenje. V tem primeru bi torej lahko avtomatično številčili člene v nekem pravnem dokumentu.

Obstaja pa še hitrejše vrivanje formul in to preprosto tako, da pritisnete kombinacijo CTRL + F9 in formulo vpišete.

Številčenje slik kot 10a, 10b

Pri vprašanju številčenja slik s pod-zaporedjem a, b, c moramo torej najprej rešiti problem trenutne prekinitve številčenja. Ko Word naleti na sliko, ki naj bi jo številčil s številko 11, mu moramo to prepovedati.

To lahko dosežemo z uporabo stikal polj (parametrov polj). Vsako polje v Wordu lahko namreč ima eno ali več stikal, ki natančneje določajo obnašanje polja. Polje SEQ tako recimo pozna stikala \c, \h, \n, \r in \s.

Stikalo, ki zanima nas je \c saj je to stikalo, ko Wordu zaukaže naj v tem primeru ne išče naslednje številke, temveč naj vzame trenutno številko:

Polje Rezultat
Slika { SEQ Slika }…. Slika 1….
Slika { SEQ Slika }…. Slika 2….
Preglednica { SEQ Preglednica }…. Preglednica 1….
Slika { SEQ Slika \c }A…. Pazi! Slika 2A….
Preglednica { SEQ Preglednica }…. Preglednica 2….
Graf { SEQ Graf }…. Graf 1….
Slika { SEQ Slika \c }B….  Pazi Slika 2B….
Graf { SEQ Graf \c }A….  Pazi! Graf 1A….
Preglednica { SEQ Preglednica }…. Preglednica 2….

Z uporabo tega stikala lahko torej prvič sliko normalno številčimo in ji dodamo črko a:

Slika { SEQ Slika }a: Pregled v januarju

Naslednjič pa uporabimo stikalo \c in dodamo črko b:

Slika { SEQ Slika }b: Pregled v februarju

Ter s tem dobimo iskani rezultat! 😉

Avtomatično številčenje v Word-u (II. del)

V prejšnjem delu smo si ogledali kako avtomatično številčiti slike v Word-u. Odprti pa sta ostali vprašanji:

  1. Kje so tu kakšna polja?
  2. Kako to sploh deluje?

Kje so tu kakšna polja?

Ko v dokument vstavimo nov napis nam Word pravzaprav vrine polje, kar je lepo in hitro vidno, če mu zaukažemo, naj nam polja prikaže.

Word seveda polja skriva in prikazuje njihov rezultat, saj je to tisto kar nas kot uporabnike zanima!

Polja razkrijete preprosto tako, da pritisnete kombinacijo ALT + F9. Z omenjeno kombinacijo polja izmenično prikazujete ~ skrivate. Če imate torej v dokumentu podnaslovljeno sliko, to izgleda takole:

word_stevilcenje3
Ko polja prikažete pa takole:

 

word_stevilcenje4S tem sem torej razložil od kot se pojavijo polja oz. zakaj takšna polja sploh osvežujemo.

Kako to sploh deluje?

Kot vidite zgoraj, Word v dokument vriva polje SEQ. Besedica SEQ izhaja oz angleščine oz. besedice sequence oz. zaporedje, kot to imenujemo na sončni strani Alp.

V kolikor bi v dokument vstavili tudi avtomatično osveževanje tabel in gantogramov, bi se nam po dokumentu pojavile sledeča polja:

 

word_stevilcenje5

Iz tega je lepo razvidno kako Word-u uspe elemente avtomatično številčiti. Vsakič ko naleti na polje SEQ pogleda napis, ki ji sledi in ta napis privzame kot element številčenja. Ko prvič naleti na nek dokument mu postavi vrednost 1, naslednjič 2, potem 3…

Postopek je torej sledeč:

Polje Rezultat
Slika { SEQ Slika }…. Slika 1….
Slika { SEQ Slika }…. Slika 2….
Preglednica { SEQ Preglednica }…. Preglednica 1….
Slika { SEQ Slika }…. Slika 3….
Preglednica { SEQ Preglednica }…. Preglednica 2….
Graf { SEQ Graf }…. Graf 1….
Slika { SEQ Slika }…. Slika 4….
Graf { SEQ Graf }…. Graf 2….
Preglednica { SEQ Preglednica }…. Preglednica 2….

 

Naslednjič pa bom odgovoril na originalno vprašanje uporabnice foruma ‘Kako doseči, da Word številči slike kot 10a in 10b‘.

 

Avtomatično številčenje v Word-u (I. del)

Oh, zmanjkalo mi je časa za redno pisanje bloga, saj sem se ukvarjal z zanimivim projektom za podjetje EGP, kjer je bila moja naloga optimizirati tisk. Zelo zanimivo, kako nastane škatlica oz. tisk na njej…

Toda seveda to ni poanta bloga, zato se vrnimo k temu, kar vam imam namen pokazati danes oz. vam bom prikazal v par naslednjih prispevkih. K pisanju je pripomoglo vprašanje uporabnice mojega foruma, ki jo je zanimalo, kako bi lahko v Word-u oblikovala dokument tako, da bi imele slike številčenje 10a, 10b in podobno. Seveda je tu govora o avtomatičnem številčenju :).

Kot vedno bomo torej najprej spoznali osnove.

Kako torej podnasloviti slike, da se bo do avtomatično številčile?

Preprosto.

  1. V Wordu označite sliko in pritisnite desni miškin gumb.
  2. Glede na verzijo Worda se vam bo odprl hitri menu z več ali manj izbirami. word_stevilcenje1
  3. Iz menija izberite opcijo Vstavi napis… In zopet se vam bo, glede na verzijo Worda, odprlo novo okno, ki je bolj ali manj podobno sledečemu: word_stevilcenje2
  4. V vsakem primeru pa boste imeli možnost napisati naslov slike (prvo vnosno polje Napis). Nikakor seveda ne izbrišite napisa ‘Slika 1’!
  5. Izbrali boste lahko drugačno oznako, saj ob številčenju seveda niste omejeni samo na slike (izbor Oznaka)
  6. In izbrali boste lahko položaj napisa; torej ali bo napis nad sliko ali pod njo (izbor Položaj).
  7. Ob teh opcijah pa imate, kot vidite, na voljo še nekaj preostalih opcij med katerimi sta uporabni predvsem dve:
  • Nova oznaka – z njo si izberete novo oznako za nek vaš element (npr. Gantagram)
  • Oštevilčenje – kjer lahko poveste ali bo v oznako slike vključena tudi številka poglavja. Včasih namreč želimo oz. potrebujemo dokument, kjer ima vsako poglavje številčene slike od 1 dalje.

Ko torej takole dodate napise k slikam, lahko slike (z napisi skupaj!) prosto premikate po dokumentu oz. jih vrivate / brišete … pa bo številčenje vedno pravilno. Seveda ne pozabite osvežiti številčenja oz. osvežiti polj! To naredite s tipko F9 (Osveži polja):

  1. Izberite celoten dokument (CTRL + A)
  2. Osvežite polja (F9).

Kakšna polja?

Vprašanje, ki se pojavi je: »Zakaj moramo osvežiti polja oz. kje so kakšna polja?«.

Na to vprašanje pa vam bom odgovoril naslednjič, ko bom razložil na kakšen način takšno avtomatično številčenje sploh deluje.

Številčenje v SQL podatkovnih bazah IV

Naslednji način pridobivanja številke (prvi del, drugi del, tretji del) pa je poenotena tabela za avtomatično številčenje različnih (poljubnih) elementov. Spet velja, da je to smiselno za MSSql in SQLite podatkovni bazi, saj Oracle pač uporablja sekvence.

Definirajmo torej enotno tablo za številčenje. Tabela bo imela 3 polja. Prvo polje je pač primarni ključ. Za to rešitev ga ne potrebujemo, vendar pa sem osebno pristaš pravila, da mora imeti vsaka tabela primarni ključ. Drugo polje je nek opis števca saj je želja, da se za vsak različen števec neodvisno številči. Tretje polje pa je pač števec sam. tabela s podatki bi torej izgledala takole:

ID   OPIS       ŠTEVILO
1    Dobavnica      1
2    Predračun      1
3    Predračun      2
4    Račun          1
5    Predračun      3
6    Račun          2
7    Dobavnica      2
8    Dobavnica      3
9    Dobavnica      4
10   Predračun      4
11   Dobavnica      5
12   Račun          3
13   Dobavnica      6

Definicija tabele

MSSql:

CREATE TABLE SEKVENCA
( ID        INT   IDENTITY(1,1)  NOT NULL
, OPIS      VARCHAR(15) NOT NULL
, STEVILO   INT         NOT NULL
);

SQLite:

CREATE TABLE SEKVENCA
( ID        INTEGER     NOT NULL
, OPIS      VARCHAR(15) NOT NULL
, STEVILO   INTEGER     NOT NULL

, PRIMARY KEY(ID)
);

Pridobivanje nove številke:

MSSql:

BEGIN TRANSACTION;
INSERT INTO SEKVENCA (OPIS, STEVILO) VALUES('racun', (SELECT COALESCE(MAX(STEVILO) + 1, 1) FROM SEKVENCA WHERE OPIS = 'racun'));
COMMIT TRANSACTION;

SQLite:

BEGIN TRANSACTION;
INSERT INTO SEKVENCA (OPIS, STEVILO) VALUES('racun', (SELECT COALESCE(MAX(STEVILO) + 1, 1) FROM SEKVENCA WHERE OPIS = 'racun'));
COMMIT TRANSACTION;

OPOMBA: Uporaba transakcije je obvezna! Na pogled se zdi, da se izvaja INSERT stavek, ki je avtonamna akcija, toda znotraj INSERT stavka se izvaja še SELECT stavek in vmes se lahko vsebina podatkov spremeni!

Številčenje v SQL podatkovnih bazah III

Naslednji način pridobivanja številke (prvi del, drugi del) je lastna tabela za vsako številčenje. Izmed omenjenih SQL podatkovnih baz (Oracle, MSSql in Sqlite) je Oracle že od nekdaj uporabljal sekvence in avtomatičnega številčenja primarnih ključev ne pozna. Za MSSql in SQLite pa je to osnovni način avtomatičnega številčenja. Kot omenjeno že zadnjič je MSSql sekvence dobil šele v reinkernaciji iz leta 2012, SQLite pa jih še vedno ne pozna.

Za avtomatično številčenje na podlagi primarnega ključa je torej potrebno to določiti že v definiciji tabele:

MSSql:

CREATE TABLE SEQ_RACUNI
(
  SID INT IDENTITY(1,1)
);

SQLite

CREATE TABLE SEQ_RACUNI
(
  SID INTEGER NOT NULL

, PRIMARY KEY(ID)
);

V obeh primerih smo določili tabelo z enim samim poljem, ki se bo avtomatično povečevalo v kolikor mu številke ne določimo. Torej:

INSERT INTO SEQ_RACUNI DEFAULT VALUES

Na ta način torej v MSSql in SQLite podatkovnih bazah dobimo avtomatično številčenje.

POZOR: Seveda pa – glede na sekvence – obstaja velika razlika. Pri sekvencah vsak zahtevek po novi številki samo poveča trenutno vrednost sekvence; v primeru avtomatičnega številčenja primarnih ključev pa se številke zapisujejo v podatkovno bazo in tako imamo za prvih 1000 številk v tabeli 1000 zapisov. To se seveda lahko preprosto reši s periodičnim brisanjem podatkovne tabele:

DELETE FROM SEQ_RACUNI WHERE SID < (SELECT MAX(SID) FROM SEQ_RACUNI)

Številčenje v SQL podatkovnih bazah II

Zadnjič sem vam omenil tri načine avtomatičnega številčenja v SQL podatkovnih bazah, danes pa vam bom prikazal prvega. Posamezne načine vam bom prikazal na primeru treh popularnih SQL baz: Oracle, MSSQL in Sqlite.

Sekvence (SEQUENCE)

Izmed omenjenih treh podatkovnih baz poznata sekvence Oracle in MSSQL (vendar MS samo od letnika 2012 dalje!). Postopek dela s sekvencami je skrajno preprost.

  1. Najprej definiramo novo sekvenco
  2. Ko potrebujemo naslednjo številko jo iz sekvence zahtevamo

To je očitno zelo dober način za pridobivanje avtomatičnih številk. Sekvenco določimo z najmanj petimi parametri (ime sekvence, minimalna vrednost, maksimalna vrednost, preskok in začetna vrednost):

CREATE SEQUENCE sequence_name
  MINVALUE value
  MAXVALUE value
  START WITH value
  INCREMENT BY value;

Primer:

CREATE SEQUENCE seq_racuni
  MINVALUE 1
  MAXVALUE 99999999
  START WITH 1
  INCREMENT BY 1;

Kot je vidno sekvenca ni omejena na zaporedno številčenje, temveč lahko številčimo tudi s korakom večjim od 1 (INCREMENT BY). Ravnotako ni nujno, da se sekvenca začne z 1 (START WITH).

OPOMBA: Seveda je z uporabo najpreprostejše srednješolske matematike tako ali tako preprosto napisati poljubno funkcijo številčenja tako da pač napišemo neko funkcijo y = F(x), kjer X pač raste od 1 do N, y pa je številka, ki nas zanima. Recimo, če želimo začeti številčiti z 8 in potem nadaljevati s korakom 15: y = 8 + 15 * (x – 1)!

Uporabiti takšno sekvenco pa je še bolj preprosto.

V Oracle jo preprosto zahtevamo s funkcijo .nextval:

SELECT seq_racuni.nextval FROM dual;

oziroma

INSERT INTO racuni
  (stevilka_racuna, znesek, datum...)
VALUES
  (seq_racuni.nextval, 1123.4, SYSDATE...);

V MSSQL pa s konstruktom NEXT VALUE FOR:

SELECT NEXT VALUE FOR seq_racuni;

oziroma

INSERT INTO racuni
  (stevilka_racuna, znesek, datum...)
VALUES
  (SELECT NEXT VALUE FOR seq_racuni, 1123.4, SYSDATE...);

Oracle Data Provider For .NET – What is Number?

Grrr… Oracle Data Provider for .NET just cost me time, (some) money and above all reputation.

My .NET application was using MS Oracle Data Provider which was OK. Many are not satisfied with it, but I had no particular problems… Until I hit BLOBs.

To be honest BLOBs are not often used in business application, so I didn’t have much knowledge on how to use it in c#. It is quite easy, but MS Oracle data provider is not fond of them.

So I was forced to use ORACLE Data provider for .NET… And – o my god – database is full of NUMBER fields so MS is using OracleType.Number, but Oracle for .NET does not know “numbers” so I was forced to change the source code from OracleType.Number to OracleDbType.Int32 or OracleDbType.Double (or something like that).

And there I made a typical programming error – typo – I one procedure I changed OracleType.Number to OracleDbType.Int32, but it was used as amount field (so double)… 🙁

And all “of the sudden” amounts were rounded to integers. Nobody noticed for 14 days… and then panic – everything is wrong – who is to blame – me – I admit (ashamed)…

BUT: Thanks Oracle, maybe guys from DB team can teach guys from .NET team what are “numbers” in DB terms…

Številčenje v SQL podatkovnih bazah

V razvoju prej ali slej naletimo na problem, ko moramo zapise številčiti. Vsakemu dokumentu pač moramo določiti edinstveno številko, ki pa mora biti ob tem še zaporedna.

Vse SQL podatkovne baze poznajo avtomatično številčenje primernega ključa – ko torej v tabelo dodamo nov zapis, slednji dobi naslednjo zaporedno številko. To imenujemo tehnično številčenje zapisov. Problem pa se pojavi, ko potrebujemo vsebinsko številko dokumenta.

Za lažje razumevanje problema, si predstavljajmo tipično podatkovno tabelo, v kateri imamo poslovne dokumente – predračune, račune, dobavnice… Vsi različni dokumenti so v isti tabeli, a vsak med njimi mora imeti lastno vsebinsko številko. Primer:

#  DOKUMENT     VSEB. ŠT.   OSTALI PODATKI

1  Predračun    PR-1/2013   ... itd ...
2  Predračun    PR-2/2013   ... itd ...
3  Račun        RA-1/2013   ... itd ...
4  Dobavnica    DO-1/2013   ... itd ...
5  Predračun    PR-3/2013   ... itd ...
6  Predračun    PR-4/2013   ... itd ...
7  Račun        RA-2/2013   ... itd ...
8  Dobavnica    DO-2/2013   ... itd ...
9  Dobavnica    DO-3/2013   ... itd ...

Kot je lepo vidno v tabeli ima vsak tip dokumenta lastno številčenje.

Kako določiti vsebinsko številko?

Opcij je seveda več a nekako jih lahko uredimo v tri sklope:

  1. Sekvence – če jih podatkovna baza podpira.
  2. Lastna tabela za vsak tip številčenja – za vsak tip dokumenta narediti lastno tabelo, ki določi naslednjo številko
  3. Ena tabela za vso številčenje – za vse številčenje uporabiti eno samo tabelo

Sekvence

Dobro

  • Rešitev namenjena temu konkretnemu problemu

Slabo

  • Ne poznajo jo vse podatkovne baze

Lastna tabela za vsako številčenje

Dobro

  • Deluje v vseh SQL bazah
  • Zelo podobna rešitev kot sekvence

Slabo

  • Veliko malih tabel
  • Vse tabele je potrebno ustvariti vnaprej ali pa v programu vedno preverjati ali tabela obstaja ali ne.

Za vso številčenje uporabiti eno samo tabelo

Dobro

  • Deluje v vseh SQL bazah
  • Preprosta rešitev
  • Ni veliko dodatnega dela

Slabo

  • Ni primerna za SQL baze z veliko hkratnimi uporabniki

V naslednjih prispevkih bom podrobneje predstavil vsako izmed možnosti…