Pieniä kysymyksiä ohjelmoinnista

Starglazer

Tukijäsen
Liittynyt
17.10.2016
Viestejä
3 092
Harjoittelen Androidilla Xamarin ohjelmointia. Olen siis täysi aloittelija. On tämä melko erikoista kun vertaa Windows C++ ohjelmointiin :D
Haluaisin siis kahden tekstirivin ja yhden napin alle taulukon. Ideana lukea viivakoodi ja hakea sen perusteella dataa ja lisätä se taulukkoon alapuolelle. Miten taulukon saa näkyviin ja sille otsikot, dataa jne? Sinänsä hauska että ZXing kirjastolla viivakoodinlukijan lisäys oli helppo nakki mutta taulukon lisäystä en osaa vielä tehdä :hmm: Löytyisikö linkkiä johonkin esimerkkiin vaikka? Pitäisikö tehdä oma xml tiedosto gridviewille ja lisätä se jotenkin LinearLayoutin alle samalle näytölle? Voiko tämä oikeasti olla näin hankalaa.

Käytössä Visual Studio 2019.

Layoutin XML tiedosto näyttää tältä:

Koodi:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    xmlns:p4="http://xamarin.com/mono/android/designer"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="vertical"
    app:layout_behavior="@string/appbar_scrolling_view_behavior"
    tools:showIn="@layout/activity_main">
    <TextView
        android:layout_width="match_parent"
        android:textAppearance="?android:attr/textAppearanceLarge"
        android:layout_height="38.0dp"
        android:layout_centerInParent="true"
        android:text="Barcode:"
        android:id="@+id/textView1" />
    <EditText
        android:layout_width="236.5dp"
        android:layout_height="53.5dp"
        android:text="540000123456"
        android:id="@+id/bCode" />
    <Button
        android:text="@string/scan_button"
        android:layout_width="wrap_content"
        android:layout_height="37.5dp"
        android:id="@+id/btScan" />
    <GridView
        android:minWidth="25px"
        android:minHeight="25px"
        android:layout_width="310.5dp"
        android:layout_height="match_parent"
        android:numColumns="4"
        android:horizontalSpacing="10dp"
        android:id="@+id/gridView1" />
</LinearLayout>
Onko tuo GridView oikein? Miten siihen saa dataa?
 

Hessu

Tukijäsen
Liittynyt
29.10.2016
Viestejä
4 420
Harjoittelen Androidilla Xamarin ohjelmointia. Olen siis täysi aloittelija. On tämä melko erikoista kun vertaa Windows C++ ohjelmointiin :D
Haluaisin siis kahden tekstirivin ja yhden napin alle taulukon. Ideana lukea viivakoodi ja hakea sen perusteella dataa ja lisätä se taulukkoon alapuolelle. Miten taulukon saa näkyviin ja sille otsikot, dataa jne? Sinänsä hauska että ZXing kirjastolla viivakoodinlukijan lisäys oli helppo nakki mutta taulukon lisäystä en osaa vielä tehdä :hmm: Löytyisikö linkkiä johonkin esimerkkiin vaikka? Pitäisikö tehdä oma xml tiedosto gridviewille ja lisätä se jotenkin LinearLayoutin alle samalle näytölle? Voiko tämä oikeasti olla näin hankalaa.

Käytössä Visual Studio 2019.

Layoutin XML tiedosto näyttää tältä:

Koodi:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    xmlns:p4="http://xamarin.com/mono/android/designer"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="vertical"
    app:layout_behavior="@string/appbar_scrolling_view_behavior"
    tools:showIn="@layout/activity_main">
    <TextView
        android:layout_width="match_parent"
        android:textAppearance="?android:attr/textAppearanceLarge"
        android:layout_height="38.0dp"
        android:layout_centerInParent="true"
        android:text="Barcode:"
        android:id="@+id/textView1" />
    <EditText
        android:layout_width="236.5dp"
        android:layout_height="53.5dp"
        android:text="540000123456"
        android:id="@+id/bCode" />
    <Button
        android:text="@string/scan_button"
        android:layout_width="wrap_content"
        android:layout_height="37.5dp"
        android:id="@+id/btScan" />
    <GridView
        android:minWidth="25px"
        android:minHeight="25px"
        android:layout_width="310.5dp"
        android:layout_height="match_parent"
        android:numColumns="4"
        android:horizontalSpacing="10dp"
        android:id="@+id/gridView1" />
</LinearLayout>
Onko tuo GridView oikein? Miten siihen saa dataa?
Riippuu millaisen taulukon haluat tehdä. Itse käyttäisin ehkä ennemmin ConstrainLayouttia, jos taulukossa ei ole kuin pari saraketta jne. Jos haluat tuonne romua niin sitten vaan koodista käsin viittaat ID:llä noihin kenttiin. En itse ole xamarinia koodannut, mutta olettaisin, että toimii suoraan, kuten java/kotlin-puolellakin. Kannattaa harmotella millaista taulukkoa olet ajatellut tuohon tekeväsi niin voi jotain arpoa miten kannattaa tehdä.
Ps. Kannattaa käyttää dp/sp/pt -määrityksiä aina pixeli -määritysten sijaan mobiilissa. Tuolla on selitetty miksi. :smile:
 
Liittynyt
08.12.2019
Viestejä
22
Xamarin toimii lähes identtisesti WPF:n kanssa.
Itse tässä kohtaa painaisin DEL:iä ja aloittaisin jostain hyvästä youtube kanavasta:



Opittavia asioita kun kuitenkin sutkot runsaasti ja päänsärky on taattu.;)
 
Liittynyt
01.01.2018
Viestejä
1 117
Laitatteko te yleensä "return typet":t typescriptissä funktioihin vai annateko vaan typescriptin arvioda palautus tyypit? Toinen kysymys on se että onko typescriptissä paljon muuta hyödyllistä opeteltavaa kuin itse tyypitys?
 
Liittynyt
17.10.2016
Viestejä
14 550
Laitatteko te yleensä "return typet":t typescriptissä funktioihin vai annateko vaan typescriptin arvioda palautus tyypit?
Riippuu vähän tilanteesta. Sen määritellyn tyypin etuina on se, että 1. se on kiva dokumentaatio siitä, mitä se funkkari palauttaa ja 2. se toimii suojana sille, ettei vahingossa muuta sen funktion palautustyyppiä kun vaikka refaktoroi. Eli lähtökohtaisesti se on musta hyödyllinen juttu. Mutta en mä sitä silti aina käytä, esim. en laita paluutyyppiä Reactin funktionaalisiin komponentteihin tai joihinkin muihin "triviaaleihin" tapauksiin.

Toinen kysymys on se että onko typescriptissä paljon muuta hyödyllistä opeteltavaa kuin itse tyypitys?
Typescriptin voi konffata tukemaan tuoreita es20xx-targetteja, jolloin saa käyttöön uusia ja ehkä itselle aiemmin tuntemattomia ominaisuuksia. Musta on todella hyödyllistä lukea Typescriptin uusien versioiden dokumentaatiot kun niitä julkaistaan. Täältä iltalukemistoa:


Suuri osa liittyy tyyppeihin mutta on siellä muutakin: onko esim. optional chaining ja nullish coalescing tuttuja syntakseja? Tai BigInt. Osasta noista voi olla hyötyä. Optional chainingia käytän hyvin paljon.

Eivät siis erityisesti vain TypeScriptin ominaisuuksia, mutta hyödyllisiä opetella.
 
Liittynyt
13.11.2016
Viestejä
1 514
Toinen kysymys on se että onko typescriptissä paljon muuta hyödyllistä opeteltavaa kuin itse tyypitys?
Onhan tossa jotain konfattavaa, vaikka sitten path aliakset tsconfigissa - saa importit vähän nätimmiksi jos relatiivisten importtipolkujen pituudet alkavat karata käsistä.
 
Liittynyt
07.01.2021
Viestejä
678
Onkohan jotain suhteellisen simppeliä tapaa tehdä tämä? Alustana Flask ja Bootstrap.

Minulla on weppisivuilla tarvetta sellaiselle datan syötölle, jossa samaan "asiaan" liittyy useampi kenttä. Tuo nyt ei varmaan asiaa selventänyt, joten esimerkki: henkilöllä voi olla muiden tietojen lisäksi n kappaletta linkkejä. Linkkiin liittyy http-osoite ja selite, esim. "Wikipedia". Toinen esimerkki on tekijäluoettelo, jossa henkilön lisäksi annetaan rooli ja mahdollinen kuvaus. Lopputulos voi siis olla jotain tyyliin "Näyttelijät: Teppo Tulppu (itsenään), Aku Ankka (itsenään), Elon Musk (Pelle Peloton)". "Näytteliä" olisi siis alasvetovalikko, henkilöt valitaan olemassaolevista ja "itsenään" ja "Pelle Peloton" tulevat vapaatekstikentästä.

Yksi näkemäni tapa on se, että ylläpidossa noita kenttiä voi lisätä olemassaolevan syötteen vieressä olevaa plussaa painamalla ja poistettua miinuksesta. Mutta jos tämän tekee käsin form-kentillä, niin tuntuu äkkiseltään aika isolta värkkäämiseltä. Pääseekö tässä jotenkin helpommalla jollain valmisratkaisulla? Olen käyttänyt select2-komponenttia aika monessa kohtaa ja sitä varmaan pitäisi pystyä käyttämään myös (ihan sen takia, että siinä on toimiva hakulogiikka ja se tukee tageja, t.s. voi luoda uusia instansseja suoraan komponentista).

Hyvä olisi, jos samalla systeemillä noiden järjestystä voisi vaihtaa.
 
Liittynyt
19.10.2016
Viestejä
1 916
Jos (ja ilmeisesti kun) kyseessä on Windows, fiksuin tapa lienee päästää bat vapaaksi helvetistä, ja ottaa käyttöön VBScript:

1. Luo esim. "start.vbs"-nimellä tiedosto
2. Lisää tiedostoon seuraava koodi:
Koodi:
CreateObject("Wscript.Shell").Run "npm run start", 0
3. ?
4. Profit

(huomiona, että tässä koko komentokehote jää aukeamatta näkyviin - mikäli haluat jättää esim. virhetilanteita varten ikkunan näkyviin, vaihda nollan (0) tilalle kaksi (2))
Heipä hei, pitkästä aikaa tässä ketjussa. Sain tämän yllä olevan vastauksen pari vuotta sitten kun kyselin:

"Noniin. Jatkokysymys jo aiemmin aloitetulle batin tekemiselle, jossa ratkaisu oli siis luoda bat-tiedosto joka ajaa asiansa ja on nyt:

@echo off
npm run start

Milläs ilveellä tuon npm run startin joka avaa erilisenn komentokehotteen auki, saa minimoitua? Nyt prompti aukeaa suoraan näytölle muun oleellisen päälle, joten pitäisi saada jätettyä auki mutta pienennettyä alapalkkiin. "


Kyhäsin vbs:n ja se toimikin tämän pari vuotta, kunnes eilen läppärinä alkoi ilmoittamaan, että tämän scriptin ajo on tietoturvaongelma.


Kysyisin nyt, että mikä on vaihtoehto vbs-filun ajamiselle wscriptiä käyttäen Windowsissa siten, että sitä ei tulkita tietoturvaongelmaksi. Tuo wscript ymmärtääkseni nyt blokataan windowsin virustorjunnan toimesta, koska se ei ole windowsin mukaan tietoturvallinen. Sisältöhän oli tämä:

CreateObject("Wscript.Shell").Run "npm run start", 2

Poikkeuksien/ohitusten lisääminen Windowsin virustorjuntaan/defenderiin ei ole ratkaisu, koska olen kokeillut lukuisilla eri tavoilla ja scriptin ajo käynnistyksen yhteydessä aina estetään.

Kansiossa x ajetaan yksinkertaisesti komento run "npm run start" ja numerolla 2 kerrotaan, että ikkuna ei jää näkyviin.
 

neko

ᓚᘏᗢ
Liittynyt
18.10.2016
Viestejä
3 751
@echo off
npm run start

Milläs ilveellä tuon npm run startin joka avaa erilisenn komentokehotteen auki, saa minimoitua? Nyt prompti aukeaa suoraan näytölle muun oleellisen päälle, joten pitäisi saada jätettyä auki mutta pienennettyä alapalkkiin. "
Toimisiko
start /min npm run start
 
Liittynyt
06.11.2016
Viestejä
944
Noob kyssäri pythonista mooc 2021 kurssin tehtävästä
break.jpg


Kuvan punaisella merkattu "loppu", miten siitä pääsee tulosteessa eroon? Tulosteen pitäisi siis syöttää nuo muuta sanat alariville kun "loppu" komento on annettu, mutta itse "loppu" ei saisi riville tulostua. Kurssimateriaaleista ja googlesta en tuohon ratkaisua löydä.
 
Liittynyt
21.10.2016
Viestejä
9 054
Noob kyssäri pythonista mooc 2021 kurssin tehtävästä


Kuvan punaisella merkattu "loppu", miten siitä pääsee tulosteessa eroon? Tulosteen pitäisi siis syöttää nuo muuta sanat alariville kun "loppu" komento on annettu, mutta itse "loppu" ei pitäisi riville enää tulostaa. Kurssimateriaaleista ja googlesta en tuohon ratkaisua löydä.
Lisäät sen jo ennen ehtolausetta sanat-muuttujaan. Tai siis, lisäät inputin aina ja lopetat vasta "loppu" sanan jälkeen. Bonuksena tehtävään: Mieti vielä miten pääset ylimääräisestä välilyönnistä eroon viimeisen sanan jälkeen.

edit: mieti kans voisitko ton ehtolauseen ajatella hieman erilailla :)¨
edit2: kannattaa opetella debuggaan. Yksinkertaisimmillaan esim. tässä tapauksessa printtaisit muuttujia tuolla whilen sisällä. Debuggerilla voisit taas steppi kerrallaan katsoa miten looppi etenee.
Esim. näin, jos ja kun lähinnä logiikkatehtävästä kyse. Ei oo python itselle tuttu.
Python:
sanat = ''

while True:
    sana = input('anna sana:')
    if sana != 'loppu':
        if sanat != '':
            sanat += ' '
        sanat += sana
    else:
        break
print(sanat)
 
Viimeksi muokattu:
Liittynyt
28.04.2020
Viestejä
47
Vaihtoehtoinen tapa saada sama tulos:
Python:
sanat=""

while True:
    sana=input("Anna sana: ")
    if sana == "loppu":
        break
    sanat += sana + " "
print(sanat.rstrip())
 

pAy

Liittynyt
15.08.2020
Viestejä
77
Käytössä ollut tuollainen sivu joka hakee kansioista aina uusimman kuvan, toiminut hyvin vanhassa webhotellissa, mutta uudessa ei toimi, mitä tuo vaatii toimiakseen? Jostain php asetuksistako johtuu toimimattomuus? Tuolla yritän käyttää...

Webhotellit - Bittivirta.cloud



PHP:
<?php
class ImageFilterIterator extends FilterIterator {
  public function accept() {
  if(preg_match('/^(?:gif|jpe?g|png)$/i',$this->getExtension())) {
  return true;
  } else {
  return false;
  }
  }
}

$dir_location = dirname(__FILE__)."/cam1";                       
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam1=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam2";                       
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam2=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam3";                       
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam3=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam4";                       
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam4=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam5";                       
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam5=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam6";                       
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam6=array_values($imageArr)[0][0];


$dir_location = dirname(__FILE__)."/cam7";                       
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam7=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam8";                       
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam8=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam9";                       
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam9=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam10";                        //
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam10=array_values($imageArr)[0][0];

header("Refresh: 300");
?>
<!doctype html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <title>Uusimmat kuvat</title>
  <style>img {width: 65%;}</style>
</head>
<body>
<?php
echo '<a href="cam1"><img src="cam1/'.$cam1.'" alt="Kamera 1"/></a><br/>';
echo '<a href="cam2"><img src="cam2/'.$cam2.'" alt="Kamera 2"/></a><br/>';
echo '<a href="cam3"><img src="cam3/'.$cam3.'" alt="Kamera 3"/></a><br/>';
echo '<a href="cam4"><img src="cam4/'.$cam4.'" alt="Kamera 4"/></a><br/>';
echo '<a href="cam5"><img src="cam5/'.$cam5.'" alt="Kamera 5"/></a><br/>';
echo '<a href="cam6"><img src="cam6/'.$cam6.'" alt="Kamera 6"/></a><br/>';
echo '<a href="cam7"><img src="cam7/'.$cam7.'" alt="Kamera 7"/></a><br/>';
echo '<a href="cam8"><img src="cam8/'.$cam8.'" alt="Kamera 8"/></a><br/>';
echo '<a href="cam9"><img src="cam9/'.$cam9.'" alt="Kamera 9"/></a><br/>';
echo '<a href="cam10"><img src="cam10/'.$cam10.'" alt="Kamera 10"/></a>';
?>
</body>
</html>
 
Liittynyt
21.10.2016
Viestejä
9 054
Käytössä ollut tuollainen sivu joka hakee kansioista aina uusimman kuvan, toiminut hyvin vanhassa webhotellissa, mutta uudessa ei toimi, mitä tuo vaatii toimiakseen? Jostain php asetuksistako johtuu toimimattomuus? Tuolla yritän käyttää...

Webhotellit - Bittivirta.cloud



PHP:
<?php
class ImageFilterIterator extends FilterIterator {
  public function accept() {
  if(preg_match('/^(?:gif|jpe?g|png)$/i',$this->getExtension())) {
  return true;
  } else {
  return false;
  }
  }
}

$dir_location = dirname(__FILE__)."/cam1";                      
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam1=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam2";                      
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam2=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam3";                      
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam3=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam4";                      
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam4=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam5";                      
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam5=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam6";                      
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam6=array_values($imageArr)[0][0];


$dir_location = dirname(__FILE__)."/cam7";                      
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam7=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam8";                      
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam8=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam9";                      
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam9=array_values($imageArr)[0][0];

$dir_location = dirname(__FILE__)."/cam10";                        //
$dir = new DirectoryIterator($dir_location);
$imageArr = array();
foreach(new ImageFilterIterator(new FilesystemIterator($dir_location)) as $fileInfo){
  if($fileInfo->isFile()){
  $cTime = new DateTime();
  $cTime->setTimestamp($fileInfo->getCTime());
  $imageArr[$fileInfo->getCTime()][] = $fileInfo->getFilename();
  }
}
krsort($imageArr);
$cam10=array_values($imageArr)[0][0];

header("Refresh: 300");
?>
<!doctype html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <title>Uusimmat kuvat</title>
  <style>img {width: 65%;}</style>
</head>
<body>
<?php
echo '<a href="cam1"><img src="cam1/'.$cam1.'" alt="Kamera 1"/></a><br/>';
echo '<a href="cam2"><img src="cam2/'.$cam2.'" alt="Kamera 2"/></a><br/>';
echo '<a href="cam3"><img src="cam3/'.$cam3.'" alt="Kamera 3"/></a><br/>';
echo '<a href="cam4"><img src="cam4/'.$cam4.'" alt="Kamera 4"/></a><br/>';
echo '<a href="cam5"><img src="cam5/'.$cam5.'" alt="Kamera 5"/></a><br/>';
echo '<a href="cam6"><img src="cam6/'.$cam6.'" alt="Kamera 6"/></a><br/>';
echo '<a href="cam7"><img src="cam7/'.$cam7.'" alt="Kamera 7"/></a><br/>';
echo '<a href="cam8"><img src="cam8/'.$cam8.'" alt="Kamera 8"/></a><br/>';
echo '<a href="cam9"><img src="cam9/'.$cam9.'" alt="Kamera 9"/></a><br/>';
echo '<a href="cam10"><img src="cam10/'.$cam10.'" alt="Kamera 10"/></a>';
?>
</body>
</html>
Mitä tarkoittaa, että ei toimi? Antaako jotain virhettä esim?
 

pAy

Liittynyt
15.08.2020
Viestejä
77
Mitä tarkoittaa, että ei toimi? Antaako jotain virhettä esim?
"
Sivu ei toimi
IP ei voi käsitellä tätä pyyntöä tällä hetkellä.


HTTP ERROR 500"

Eli ei avaa koko sivua, jos laittaa jonkin pelkän html-koodin pätkän niin se avautuu.
 
Liittynyt
21.10.2016
Viestejä
9 054
"
Sivu ei toimi
IP ei voi käsitellä tätä pyyntöä tällä hetkellä.


HTTP ERROR 500"

Eli ei avaa koko sivua, jos laittaa jonkin pelkän html-koodin pätkän niin se avautuu.
Tarttis ne php-virheet nähdä, siihen liittyy. webhotelli ei välttis jotain tue tai oikeuksia puuttuu tms..
 

pAy

Liittynyt
15.08.2020
Viestejä
77
Tarttis ne php-virheet nähdä, siihen liittyy. webhotelli ei välttis jotain tue tai oikeuksia puuttuu tms..
Logissa näkyy tuollainen, en tiedä onko siinä mitään mistä näkee?

AH01071: Got error 'PHP message: PHP Fatal error: Uncaught UnexpectedValueException: DirectoryIterator::__construct(/vol-1/xxxxxxxxxxx/httpdocs/cam1): Failed to open directory: No such file or directory in /vol-1/xxxxxxxxxxxxx/httpdocs/index.php:13\nStack trace:\n#0 /vol-1/xxxxxxxxxxxxx/httpdocs/index.php(13): DirectoryIterator->__construct()\n#1 {main}\n thrown in /vol-1/xxxxxxxxxxxx/httpdocs/index.php on line 13'
 
Liittynyt
17.10.2016
Viestejä
4 589
Logissa näkyy tuollainen, en tiedä onko siinä mitään mistä näkee?

AH01071: Got error 'PHP message: PHP Fatal error: Uncaught UnexpectedValueException: DirectoryIterator::__construct(/vol-1/xxxxxxxxxxx/httpdocs/cam1): Failed to open directory: No such file or directory in /vol-1/xxxxxxxxxxxxx/httpdocs/index.php:13\nStack trace:\n#0 /vol-1/xxxxxxxxxxxxx/httpdocs/index.php(13): DirectoryIterator->__construct()\n#1 {main}\n thrown in /vol-1/xxxxxxxxxxxx/httpdocs/index.php on line 13'
No eikö tuo ole aika selkeä: kansiota '/vol-1/xxxxxxxxxxx/httpdocs/cam1' ei löydy.
 
Liittynyt
21.10.2016
Viestejä
9 054
Logissa näkyy tuollainen, en tiedä onko siinä mitään mistä näkee?

AH01071: Got error 'PHP message: PHP Fatal error: Uncaught UnexpectedValueException: DirectoryIterator::__construct(/vol-1/xxxxxxxxxxx/httpdocs/cam1): Failed to open directory: No such file or directory in /vol-1/xxxxxxxxxxxxx/httpdocs/index.php:13\nStack trace:\n#0 /vol-1/xxxxxxxxxxxxx/httpdocs/index.php(13): DirectoryIterator->__construct()\n#1 {main}\n thrown in /vol-1/xxxxxxxxxxxx/httpdocs/index.php on line 13'
Juu, en nyt muista miten php noissa käyttäytyy, mut joko ei oikeuksia (oletan, että kansio on olemassa? Jos ei niin pitää luoda tietenkin) tai sit sun pitää viitata kansioon erilailla. esim. "/vol-1/xxxxxxxxxxx/httpdocs/cam1" sijaan "./cam" tai "cam"
 

pAy

Liittynyt
15.08.2020
Viestejä
77
No siitähän se oli prkl... en huomannut ennemmin tuota logia katsoa kun testailin. Kiitos avusta!
 

jad

Liittynyt
22.10.2016
Viestejä
1 210
Käytössä ollut tuollainen sivu joka hakee kansioista aina uusimman kuvan, toiminut hyvin vanhassa webhotellissa, mutta uudessa ei toimi, mitä tuo vaatii toimiakseen?
Sinällään ihan täysin tiomivaa ja validia koodia, mutta itseni kaltainen laiska mistään mitään välittämätön koodari olisi tuon voinut toteuttaa myös näin:
PHP:
<?php
header("Refresh: 300");
?>
<!doctype html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <title>Uusimmat kuvat</title>
  <style>img {width: 65%;}</style>
</head>
<body>
<?php
echo '<a href="cam1"><img src="'.array_pop(glob('cam1/*.jpg')).'" alt="Kamera 1"/></a><br/>';
echo '<a href="cam2"><img src="'.array_pop(glob('cam2/*.jpg')).'" alt="Kamera 2"/></a><br/>';
echo '<a href="cam3"><img src="'.array_pop(glob('cam3/*.jpg')).'" alt="Kamera 3"/></a><br/>';
echo '<a href="cam4"><img src="'.array_pop(glob('cam4/*.jpg')).'" alt="Kamera 4"/></a><br/>';
echo '<a href="cam5"><img src="'.array_pop(glob('cam5/*.jpg')).'" alt="Kamera 5"/></a><br/>';
echo '<a href="cam6"><img src="'.array_pop(glob('cam6/*.jpg')).'" alt="Kamera 6"/></a><br/>';
echo '<a href="cam7"><img src="'.array_pop(glob('cam7/*.jpg')).'" alt="Kamera 7"/></a><br/>';
echo '<a href="cam8"><img src="'.array_pop(glob('cam8/*.jpg')).'" alt="Kamera 8"/></a><br/>';
echo '<a href="cam9"><img src="'.array_pop(glob('cam9/*.jpg')).'" alt="Kamera 9"/></a><br/>';
echo '<a href="cam10"><img src="'.array_pop(glob('cam10/*.jpg')).'" alt="Kamera 10"/></a>';
?>
</body>
</html>
Tämä toimii sillä oletuksella, että kameroiden lähettämät kuvat on nimetty siten, että aakkosjärjesys=aikajärjestys. Jos näin ei ole, niin glob funktioon lippu GLOB_NOSORT
 
Liittynyt
01.01.2018
Viestejä
1 117
Jos hashaa salasanan bcryptillä niin eikä sitä saa mitenkään enää siitä takasin niin miten toi bcrypt. Compare oikein voin toimia ollenkaan?

Onko teillä preferenssiä sen suhteen että käyttääkö orm tekniikoita vai suoraan sql komentoja nodejs ohjelmassa? Omassa harjoitus projektissa olen käyttänyt typeormia ja typegraphql koska sillä saa tosiaan noi tyypit sitten.
 
Liittynyt
19.10.2016
Viestejä
3 411
Jos hashaa salasanan bcryptillä niin eikä sitä saa mitenkään enää siitä takasin niin miten toi bcrypt. Compare oikein voin toimia ollenkaan?
Vertausta varten käyttäjän syöttämä salasana hashataan myös, samoilla asetuksilla. Näitä hasheja sitten verrataan.
 
Liittynyt
17.10.2016
Viestejä
14 550
Jos hashaa salasanan bcryptillä niin eikä sitä saa mitenkään enää siitä takasin niin miten toi bcrypt. Compare oikein voin toimia ollenkaan?
Hash on yksisuuntainen funktio. Eli on mahdotonta tietää, mistä alkuperäisestä datasta (salasanasta) tietty hash on muodostettu. Mutta ei onneksi tarvitsekaan. Tietokantaan tallennetaan käyttäjien salasanojen (ja suolan) hash-arvot. Sitten kun joku käyttäjä yrittää kirjautua, tämän täytyy antaa salasana. Bcrypt siis laskee tälle kokeiltavalle salasanalle samalla tavalla hash-arvon ja vertaa sitä tietokannassa olevaan arvoon. Jos ne ovat samat, niin tiedetään, että salasanatkin olivat samoja. Silti salasanaa ei tarvitse tallettaa mihinkään, ja se pysyy salassa.

Suola estää tietyn hyökkäyksen tekemisen lisäämällä satunnaisen merkkijonon hashattavaan salasanaan ennen hashaystä. Näin ei voida käyttää isoja ennalta laskettujen hashien tietokantaa apuna murrossa.

Onko teillä preferenssiä sen suhteen että käyttääkö orm tekniikoita vai suoraan sql komentoja nodejs ohjelmassa? Omassa harjoitus projektissa olen käyttänyt typeormia ja typegraphql koska sillä saa tosiaan noi tyypit sitten.
Yleensä menee niin, että orm:lla päästään jonnekin asti, ja siten kun ei päästä pidemmälle, täytyy sekaan laittaa raakaa SQL:ää.
 
Liittynyt
28.01.2017
Viestejä
469
Täysi aloittelija SQL:n parissa. Miten tuollainen kysely rakennetaan?
1.png
 
Liittynyt
28.01.2017
Viestejä
469
On kyllä todellakin niin täysin alkeita relaatiotietokannoista, että jos on tarkoitus oppia, niin ei kannata valmista vastausta pyytää.
En tarvitse valmista vastausta, mutta koita ymmärtää ja suhteuttaa tämä totaalisen aloittelijan silmin. Olen kyllä asiaa koittanut pyörittää jo hyvän tovin itsekseni, mutta todennäköisesti ajattelen tätä nyt täysin väärältä kantilta kun se ei aukea. Tarvitaanko tuossa JOIN-syntaksia vai mitä tuohon kannattaa käyttää?
 
Liittynyt
17.10.2016
Viestejä
4 589
En tarvitse valmista vastausta, mutta koita ymmärtää ja suhteuttaa tämä totaalisen aloittelijan silmin. Olen kyllä asiaa koittanut pyörittää jo hyvän tovin itsekseni, mutta todennäköisesti ajattelen tätä nyt täysin väärältä kantilta kun se ei aukea. Tarvitaanko tuossa JOIN-syntaksia vai mitä tuohon kannattaa käyttää?
Aina tarvitsee joinia kun yhdistellään tietoja useammasta taulusta, mutta tässä tapauksessa se join on aika yksinkertaista. Katso vaikka täältä mallia: SQL - Using Joins

Jos tuo on joku tehtävä, niin luulisi että ennen sitä olisi asia opetettu?
 
Liittynyt
07.01.2021
Viestejä
678
Pitäisi mennä ihan taulualiaksilla. Eli voit määritellä kyselyn niin, että kaupungit-taulua voi käsitellä kahtena eri instanssina (?). Kysely on niin simppeli tuon jälkeen, että en oikein tiedä miten vihjaista tämän enempää ilman, että ratkaisen tehtävän puolestasi.

Eli googlaa "sql table alias".
 
Liittynyt
28.01.2017
Viestejä
469
Pitäisi mennä ihan taulualiaksilla. Eli voit määritellä kyselyn niin, että kaupungit-taulua voi käsitellä kahtena eri instanssina (?). Kysely on niin simppeli tuon jälkeen, että en oikein tiedä miten vihjaista tämän enempää ilman, että ratkaisen tehtävän puolestasi.

Eli googlaa "sql table alias".
Kiitos, tällä aukesi melkeinpä heti.
 
Liittynyt
17.10.2016
Viestejä
4 589
Pitäisi mennä ihan taulualiaksilla. Eli voit määritellä kyselyn niin, että kaupungit-taulua voi käsitellä kahtena eri instanssina (?). Kysely on niin simppeli tuon jälkeen, että en oikein tiedä miten vihjaista tämän enempää ilman, että ratkaisen tehtävän puolestasi.

Eli googlaa "sql table alias".
No ei tuo pelkillä aliaksilla onnistu vaan lisäksi pitää tehdä inner join, joka tosin tässä tapauksessa onnistuu implisiittisesti ilman että mitään join-syntaksia pitää kirjoittaa.
 
Liittynyt
07.01.2021
Viestejä
678
No siis tietysti pitää lisätä ehtolause, mutta eipä tässäkään tapauksessa rautalankaa tarvittu.
 
Liittynyt
28.01.2017
Viestejä
469
Aloittelijana sitä ajautuu perusasioissakin joskus todella tyhmiin umpikujiin, mistä ei osaa enää peruuttaa pois. Se varmaan näyttää kokeneemmalle typerältä, mutta joskus pelkästään jo uuden näkökulman antaminen (tässä tapauksessa aliakset) helpottaa ajattelemaan asiaa uudelta kannalta ja ratkaisemaan tehtävän.
 
Liittynyt
20.10.2016
Viestejä
778
Miksi mun juttu ei toimi?

merkkjono §12-34

haluan korvata väliviivan madolla ~ jos pykälän ja viivan välissä on tasan kaksi numeroa

§123-34 tätä ei saa muuttaa eikä §5-34

Yritin

echo §12-34 | sed -r "s/(?:\§[0-9]{2})\-/\~/"

jolloin tuo pykälä ja kaksi numeroa olisi non-capture group, mutta se vastaa §12-34 eikä §12~34
 
Liittynyt
02.11.2016
Viestejä
1 174
Miksi mun juttu ei toimi?

merkkjono §12-34

haluan korvata väliviivan madolla ~ jos pykälän ja viivan välissä on tasan kaksi numeroa

§123-34 tätä ei saa muuttaa eikä §5-34

Yritin

echo §12-34 | sed -r "s/(?:\§[0-9]{2})\-/\~/"

jolloin tuo pykälä ja kaksi numeroa olisi non-capture group, mutta se vastaa §12-34 eikä §12~34
Onko pakko käyttää sediä?

Koodi:
echo §12-24 | perl -pe 's/(§[0-9]{2})-([0-9]{2})\b/\1~\2/'
 
Liittynyt
17.10.2016
Viestejä
5 331
Noita regexpejä on helpon testata esim. regex101.com:ssa. Tuolla minä aina rakennan vähänkin monimutkaisemmat.
Sama vika, suosittelen ehdottomasti. Todella näppärä kikkailla regexpejä kun saa kasan dataa copypastetettua ja voi livenä arpoa sopivaa regexpiä. Olisi manuaalisesti ainakin monimutkaisemmissa regexpeissä työlästä tehdä itse sopivaa omaa vastaavaa toiminnallisuutta kun tuolla saa hetkessä tstailtua sopivat säännöt.
 
Liittynyt
17.01.2018
Viestejä
1 997
Tämän tyyppisissä muutaman rivin tehtävissä ei niin väliä, mutta jos tauluissa on paljon rivejä niin ratkaisumallilla on traaginen merkitys suoritusnopeuteen.
Kannattaa siis opetella heti alusta lähtien välttämään alikyselyitä.

SQL:
SELECT
    MISTA.NIMI AS KAUPUNKI_MISTA,
    MINNE.NIMI AS KAUPUNKI_MINNE
FROM
    LENNOT L,
    KAUPUNGIT MISTA,
    KAUPUNGIT MINNE
WHERE
    L.MISTA_ID = MISTA.ID
AND L.MINNE_ID = MINNE.ID
 
Liittynyt
07.02.2018
Viestejä
125
Tämän tyyppisissä muutaman rivin tehtävissä ei niin väliä, mutta jos tauluissa on paljon rivejä niin ratkaisumallilla on traaginen merkitys suoritusnopeuteen. Kannattaa siis opetella heti alusta lähtien välttämään alikyselyitä.
---
Itse suosin mahdollisimman selkeitä SQL-kyselyjä. Kyselyitä voi tarpeen mukaan optimoida.

Microsoftin SQL Serverin dokumentaatio vuodelta miekka ja kivi (2008):

Many Transact-SQL statements that include subqueries can be alternatively formulated as joins. Other questions can be posed only with subqueries. In Transact-SQL, there is usually no performance difference between a statement that includes a subquery and a semantically equivalent version that does not. However, in some cases where existence must be checked, a join yields better performance...

Verkosta löytyi myös aika tekninen artikkeli, jossa kuvataan miten tietokannat toimivat, ja kuinka mm. alikyselyitä pyritään mm. muuttamaan JOINeiksi (engl. subquery flattening) tietokannan sisällä:


Näiden lisäksi Stackoverflowsta löytyy "join vs subquery" väittely, jossa osa väittää JOINeja "ainoaksi oikeaksi tavaksi" ja osalla alikysely hakkaa miljoonan rivin taulussa JOINin. Oikeasti kyse on tietokannan rakenteesta, indekseistä, datan määrästä ja itse SQL-kyselystä. SQL-kyselyn testaaminen kannattaa reaalimaailmassa ja lopulta nopeuteen vaikuttaa myös itse toteutus ts. ORM Mapper vs. DB Stored Procedures vs. suoraan koodista SQL-kysely.

Tosin epäilen vähän, että tehtävässä vaaditaan JOINia, ei alikyselyitä SELECTillä. Menee vielä kurssin vetäjällä herneet nenään, jos esittelee muuta kuin odotettuja SQL-kyselyitä.
 
Viimeksi muokattu:
Liittynyt
17.01.2018
Viestejä
1 997
---
Itse suosin mahdollisimman selkeitä SQL-kyselyjä. Kyselyitä voi tarpeen mukaan optimoida.

Tosin epäilen vähän, että tehtävässä vaaditaan JOINia, ei alikyselyitä SELECTillä. Menee vielä kurssin vetäjällä herneet nenään, jos esittelee muuta kuin odotettuja SQL-kyselyitä.
Tottakai selkeys kannattaa olla myös mukana.

Jos menisi oikein niin kurssilla pitäisi kyllä hyväksyä mikä tahansa kysely joka tuottaa oikean tuloksen ja esittää se jota haettiin (ja miksi juuri se).

Minulle nämä ovat kyllä selviä (rakenteet, optimointi, indeksit ja tiesmitkä) kun on viimeiset reilu 20 vuotta tullut tehtyä kantahommia.
En aio lähteä kinaamaan mutta mielestäni alikyselyt eivät ole se malli josta kannattaa lähteä liikkeelle jo selkeydenkin vuoksi. Kyselyn plan tietysti kertoo onko merkitystä juuri omassa tapauksessa.
 
Liittynyt
08.02.2019
Viestejä
1 251
Tosin epäilen vähän, että tehtävässä vaaditaan JOINia, ei alikyselyitä SELECTillä. Menee vielä kurssin vetäjällä herneet nenään, jos esittelee muuta kuin odotettuja SQL-kyselyitä.
Kyllä näin voisi olettaa, että JOINien harjoittelu kyseessä. Eli kyselyhän menisi siis JOINeilla näin:
Koodi:
SELECT
  k1.name AS mistä, k2.name AS minne
FROM
  lennot l JOIN
  kaupungit k1 ON k1.id = l.mista_id JOIN
  kaupungit k2 ON k2.id = l.minne_id
Tämä siis postgres syntaxi ja vielä sqlfiddle esimerkki:
Screenshot 2021-09-23 at 12.34.06.png

Sitten taas tehokkuus erot on toki täysin kanta kohtaisia. Ja tosiaan tässäkin kannattaisi indeksoida lennot mista_id, lennot minne_id sekä kaupungit id, jolloin tehokkuus on ihan omaa luokkaansa verrattuna siihen, että käydään näitä raa'asti tauluista läpi. Ja kyllä, tämän huomaa viimeistään, kun insertoi kaikki lentokentät maailmasta ja 20 vuoden lennot.
 
Viimeksi muokattu:
Liittynyt
17.01.2018
Viestejä
1 997
Tässä menee helposti sekaisin join (siis taulujen välinen liitos kyselyssä tavasta riippumatta) ja join- termillä toimiva syntaksi.

Tehtävässähän ei pyydetty tiettyä syntaksia vaan tulosta jolloin kaikkien versioiden (myös alikyselymalli) pitäisi olla "oikein". Käytännössä molemmat mallit pitäisi tietysti osata ja toivottavasti on esitetty myös materiaalissa/kurssilla.

Sama join- termillä toteutettu liitos toimii ainakin mssql, oracle, athena, snowflake, mysql/mariadb, postgres- kannoissa, nykyään on enää aika vaikea sanoa mikä on minkäkin kannan oma syntaksi kun samat kyselyt toimii niin monessa (paitsi funktiot tahtoo olla erilaisia).
 
Liittynyt
08.02.2019
Viestejä
1 251
Tässä menee helposti sekaisin join (siis taulujen välinen liitos kyselyssä tavasta riippumatta) ja join- termillä toimiva syntaksi.

Tehtävässähän ei pyydetty tiettyä syntaksia vaan tulosta jolloin kaikkien versioiden (myös alikyselymalli) pitäisi olla "oikein". Käytännössä molemmat mallit pitäisi tietysti osata ja toivottavasti on esitetty myös materiaalissa/kurssilla.
Oikeastaan tähän voisin sen verran sanoa, että WHERE lause on SQL:ssä tarkoitettua filterointiin, jolla voidaan valita rivit, jotka otetaan mukaan tulosjoukkoon. Esimerkiksi joku kenttä on TRUE toinen FALSE, tai arvo on yli > 100 tai mitä ikinä.

Kun taas JOINit on ollut käytössä ainakin SQL-92:sta asti juuri taulujen liittämiseen. Jos kirjoitat kyselyn, jossa oikeasti filteroit useita asioita WHERE ehdolla ja kysely kohdistuu vaikka 12 tauluun, niin voin sanoa, että tulee aikamoinen sillisalaatti, jos käytät WHERE ehtoa myös taulujen liittämiseen. JOINeilla pystyt saman kirjoittamaan täysin erilleen siististi ja myös ottamaan huomioon sen, että jos haluat liittää tauluja, joissa toisessa on esimerkiksi NULL-arvoja id:n paikalla tai jotain muuta, mikä ei '='-merkillä toimi.

SQL Fiddle näyttää olevan hiukan 'jäässä', mutta kokeillaan DB-fiddleä, saat ehkä ideasta kiinni mitä ei voi tehdä WHERE lauseella, mutta LEFT JOINilla kylläkin:

Eli jos ajat sen kommentoidun selectin, jossa on WHERE lause, niin se filteroi joukkoa (samoin kuin JOIN), kun taas LEFT JOIN tässä tapauksessa ei filteroi ja silti liittää osuvat yhteen.
 
Liittynyt
17.01.2018
Viestejä
1 997
Oikeastaan tähän voisin sen verran sanoa, että WHERE lause on SQL:ssä tarkoitettua filterointiin, jolla voidaan valita rivit, jotka otetaan mukaan tulosjoukkoon. Esimerkiksi joku kenttä on TRUE toinen FALSE, tai arvo on yli > 100 tai mitä ikinä.
Tähän sanoisin kyllä ja ei. Alunperin silloin kun aloitin työt kantojen kanssa niin suurin osa kaikista tehdyistä meni vain FROM WHERE syntaksilla. Join- syntaksi oli joissakin kannoissa mutta kaikissa ei (esimerkisi oracle).
Ja voithan tehdä saman vaikka FROM a JOIN b ON a.a = b.a AND b.b = 1, sekin rajaa pois arvoja samalla tavalla kuin FROM a JOIN b ON a.a = b.a WHERE b.b = 1 tai FROM a, b WHERE a.a = b.a AND b.b = 1.

Kun taas JOINit on ollut käytössä ainakin SQL-92:sta asti juuri taulujen liittämiseen. Jos kirjoitat kyselyn, jossa oikeasti filteroit useita asioita WHERE ehdolla ja kysely kohdistuu vaikka 12 tauluun, niin voin sanoa, että tulee aikamoinen sillisalaatti, jos käytät WHERE ehtoa myös taulujen liittämiseen. JOINeilla pystyt saman kirjoittamaan täysin erilleen siististi ja myös ottamaan huomioon sen, että jos haluat liittää tauluja, joissa toisessa on esimerkiksi NULL-arvoja id:n paikalla tai jotain muuta, mikä ei '='-merkillä toimi.
Ah, taas päästään väittelyyn. Vastaan on tullut molemmilla tavoilla tehtyjä isoja kyselyitä jotka ovat omalla tavallaan hankalia kummalla tahansa mallilla.
Null- arvojen käsittelyyn tuolla ei ole merkitystä (eikä tässä käsitellyssä tapauksessa) koska FROM a, b WHERE a.a = b.a tai FROM a JOIN b ON a.a = b.a käsittelee null- arvot samalla tavalla, ehto joko täsmää tai ei. Toiminta riippuu kannasta, toisissa toimi ja toisissa ei. Outer join on tietysti eri asia, ei mennä siihen nyt.
Voitaisiin myös kinastella siitä pitääkö käyttää mallia FROM a JOIN b ON ( a.a = b.a ) suluilla vai ilman... koska ilman sulkuja isot kyselyt ovat enemmän salaattia kuin suluilla varsinkin jos ehtoja on enemmän kuin yksi. Tämäkin on varmaan mielipidekysymys.

SQL Fiddle näyttää olevan hiukan 'jäässä', mutta kokeillaan DB-fiddleä, saat ehkä ideasta kiinni mitä ei voi tehdä WHERE lauseella, mutta LEFT JOINilla kylläkin:

Eli jos ajat sen kommentoidun selectin, jossa on WHERE lause, niin se filteroi joukkoa (samoin kuin JOIN), kun taas LEFT JOIN tässä tapauksessa ei filteroi ja silti liittää osuvat yhteen.
Jaa, oliko jossain tässä keskustelussa jo mainittu left join ? Ainakaan omaan silmään ei osunut muualla kuin tässä viimeisessä.
Se on tietysti eri asia mutta jos tekee FROM a, b WHERE a.a = b.a tai FROM a JOIN b ON a.a = b.a tulosjoukko on kyllä sama, left (outer) join ei taida olla missään kannassa oletuksena.

Tarkoitukseni oli esittää asia niin että siitä olisi ollut jotain hyötyä kysyjälle joka kertoi olevansa täydellinen aloittelija. Ilmeisesti onnistuin taas vaan sohaisemaan väärään paikkaan ;)

Ja pienenä toistona, itse en tunne tarvitsevani ideoita miten kyselyt toimivat.
Jätän tämän nyt tähän.
 
Liittynyt
08.02.2019
Viestejä
1 251
@ississ Jeps ei ollut tarkoitus käynnistää mitään väittelyä, tosiaan kaikki kolme tapaa oikein (jopa ne alikyselyt). Koko homman pointti oli vaan se, että miten SQL-syntaxi on tehty, eli WHERE filteroi ja JOIN liittää. Jos kanta ei tue standardia, niin se ei tietenkään ole standardin vika. Itse myös vuosia DBA:n hommia tehneenä on jokunen kysely tullut kirjoitettua. Minun puolestani jokainen tosiaan saa kirjoittaa kyselyt tyylillään, pääasia, että toimii, joten lopetan myös tähän. :)
 
Liittynyt
14.10.2017
Viestejä
620
Olen käyttänyt tietokoneita "aina" ja ison osan ajasta koodannutkin, mutta en ole ikinä kirjoittanut riviäkään SQL:ää. En tajua yllä olevasta keskustelusta mitään. Mikäköhän olisi tehokas tapa näin "vanhemmalla iällä" opetella SQL:ää ja muita tietokantajuttuja, jos taustalla on tekniikan tohtorin tutkinto ja todennäköisesti ihan riittävä ymmärrys tietorakenteista ja algoritmeista? Onko esim. jotain hyvää kirjaa?
 
Toggle Sidebar

Statistiikka

Viestiketjut
237 394
Viestejä
4 159 661
Jäsenet
70 409
Uusin jäsen
allun90

Hinta.fi

Ylös Bottom