1. Ik snap even niet.quote:Op dinsdag 24 maart 2009 19:10 schreef GlowMouse het volgende:
[..]
Je kunt bijvoorbeeld zeggen: WHERE id = (SELECT max(id) FROM fotoboek_comments WHERE ...)
Flaccid:
1. Domtree of regex, kies maar
2. Wat is per entry? je wilt van élk record 2 velden? Dat is snel maar je moet geen duizenden records hebben.
3. Zoek eens op xmlHttpRequest, er komt wat JavaScript en PHP bij kijken
Hoezo zou het niet werken? Werkt bij mij anders perfect...quote:Op dinsdag 24 maart 2009 18:59 schreef GlowMouse het volgende:
[..]
Ziet er leuk uit, maar wekt niet. DISTINCT gaat over een rij.
Knappe studiebol ben je dat je aan de hand van 1 table kan zien hoe zijn datamodel eruit ziet. Jij hebt zeker de glazen bol gejat die iedereen mist (zie OP).quote:Daar heb ik voor geleerd. Met dit datamodel krijgt hij die query onmogelijk snel tenzij er slechts een beperkt aantal records in de tabel zit.
Uit nieuwsgierigheid, wat is je query en waar kunnen we het resultaat zien?quote:Op dinsdag 24 maart 2009 19:59 schreef qwox het volgende:
ik heb me probleem weten op de lossen met een subquery, volgens mij is die niet optimaal maar dat maakt niet uit.
Het is een script op de website van een studentenvereniging, ik weet 100% zeker dat er slechtere code te vinden is op die site.
bedankt voor de hulp
thanks, je hebt me op een idee gebracht die ook nog werkt..quote:Op dinsdag 24 maart 2009 18:44 schreef GlowMouse het volgende:
Kijken wanneer het plaatje voor het laatst is aangepast, en indien lang genog, een ander plaatje tonen?
En welk idee is dat?quote:Op dinsdag 24 maart 2009 23:48 schreef bassiedekloon het volgende:
thanks, je hebt me op een idee gebracht die ook nog werkt..
het is niet super maar werkt wel goed![]()
http://dev.mysql.com/doc/refman/5.1/en/select.htmlquote:Op dinsdag 24 maart 2009 19:59 schreef slacker_nl het volgende:
[..]
Hoezo zou het niet werken? Werkt bij mij anders perfect...
Daar heb je geen glazen bol voor nodig. Ik zal je de algemene regel schenken: wanneer je wilt sorteren op kolom A en slechts één A wilt bij iedere unieke waarde uit kolom B (met B ongelijk A) dan kan MySQL die query niet efficiënt uitvoeren.quote:Knappe studiebol ben je dat je aan de hand van 1 table kan zien hoe zijn datamodel eruit ziet. Jij hebt zeker de glazen bol gejat die iedereen mist (zie OP).
Subqueries zie ik ook liever niet, maar die zijn er niet voor niks. Als de functionaliteit van de applicatie iets vereist dat alleen met subqueries op te lossen is, dan kom je er in sommige gevallen niet onderuit.quote:Op woensdag 25 maart 2009 12:36 schreef GlowMouse het volgende:
Daar heb je geen glazen bol voor nodig. Ik zal je de algemene regel schenken: wanneer je wilt sorteren op kolom A en slechts één A wilt bij iedere unieke waarde uit kolom B (met B ongelijk A) dan kan MySQL die query niet efficiënt uitvoeren.
Als je 30k reacties hebt en je query heeft 60+ seconden nodig, dan staan je indices niet goed. Misschien moet je ook de query zelf aanpassen, maar goed geplaatste indices doen heel veel.quote:Op woensdag 25 maart 2009 13:01 schreef GlowMouse het volgende:
Websites moeten snel zijn omdat dat fijn is voor de gebruikeren omdat je server dan meer bezoekers aan kan. Voor je back-end zijn subqueries minder erg en kunnen ze soms leuke statistieken tevoorschijn toveren.
Per geval kun je nadenken wat je het beste kunt doen. Soms valt de query iets te herschrijven. Hier is dat niet mogelijk, dus zul je het resultaat moeten cachen.
Deze query gaat er bij een wat grotere dataset seconden over doen (benchmark: 60+ seconden bij 30k reacties) en dat is onacceptabel. MySQL kan hem slecht cachen omdat de reactietabel vaak geüpdatet wordt. Dus dan moet je applicatie maar helpen.
Je hebt gelijk, subquery met LIMIT en een tweetal indices doet wonderen hier. Blijft een relatief langzame query, maar het is nu te overzien (paar honderdsten van een seconde, afhankelijk van waar de laatste reacties geplaatst zijn).quote:Op woensdag 25 maart 2009 13:12 schreef Tuvai.net het volgende:
Sowieso is je voorbeeld erg overdreven. Op iets eenvoudigs als een reactie-tabel, kun je toch snelle queries draaien waar subqueries in zitten. Sowieso haal je in geval van reacties altijd maar een bepaald aantal op (hee, LIMIT), en zit er in die reactie-tabel een veld dat verwijst naar de bovenliggende tabel (hee, een INDEX
). Als er honderdduizenden records in die reactie tabel zitten dan zal die ietsjes langzamer zijn dan wanneer er maar 10 records in zitten, maar 60+ seconden?
Kom op zeg.
Extra veld in de rubriektabel.quote:Ik geef je eens een ander voorbeeld. Stel je hebt een webshop met rubrieken. Die rubrieken zijn dusdanig opgezet dat je onbeperkt diep child-rubrieken kunt aanmaken onder bestaande rubrieken. Van elke rubriek wil je het actuele aantal producten in diezelfde rubriek en diens onderliggende rubrieken hebben. Hoe zou jij dat oplossen?
Zo 'relatief' langzaam dat de gebruiker er niks van merkt. Ook in geval van honderdduizenden records niet. Die paar milliseconden op zo veel records zijn verwaarloosbaar, vooral als dat de schaalbaarheid, overzichtelijkheid en flexibiliteit van de broncode ten goede doet.quote:Op woensdag 25 maart 2009 13:38 schreef GlowMouse het volgende:
Je hebt gelijk, subquery met LIMIT en een tweetal indices doet wonderen hier. Blijft een relatief langzame query, maar het is nu te overzien (paar honderdsten van een seconde, afhankelijk van waar de laatste reacties geplaatst zijn).
Dus elke keer wanneer een product toegevoegd of verwijdert wordt ga je alle rubrieken (en subrubrieken, en diens subrubrieken, enz) nalopen, het aantal producten in die rubriek (en subrubrieken, en diens subrubrieken) met een COUNT(*) ophalen en die waarde wegschrijven? Waar leg je die functionaliteit en hoe doe je dat dan?quote:Op woensdag 25 maart 2009 13:38 schreef GlowMouse het volgende:
Extra veld in de rubriektabel.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | - - A A - - - A A A - - - A A B - - - A A C - - A B - - - A B A - - - A B B - - - A B C - - A C - - - A C A - - - A C B - - - A C C - - A D - - - A D A - - - A D B - - - A D C - - A E - - - A E A - - - A E B - - - A E C - - A F - - - A G A - - - A G B - - - A G C |
1 2 3 4 5 6 7 8 9 | $lines = array("<td>{=test}</td>", "<td>{te=st}</td>", "<td>{test=}</td>"); $regexp = '/(\{)(\w+)?=?(\w+)?(\})/'; foreach ($lines as $v) { print preg_replace($regexp, '\1\2\3\4', $v); } ?> |
Beter bij het updaten dan bij het opvragen. Bij een webwinkel gebeurt dat laatste veel vaker. En als je voor je site die getallen veel nodig hebt, dan ga je denormaliseren. Gebeurt ook veel in fora, bijvoorbeeld de berichtenteller, zie phpbb, zie vbulletin, zie myreact.quote:Op woensdag 25 maart 2009 13:48 schreef Tuvai.net het volgende:
Stel je verwijdert een product in rubriek '- - - A E C', dan zal het productaantal van rubriek '- A' ook actueel moeten worden. Erg veel COUNT(*) query`tjes zeg.
Dan bouw je een knop in waarmee alle tellers opnieuw berekend worden.quote:Wat doe je overigens als een DBA in 'geval van nood' een product via de database moet verwijderen of 'recoveren'?
Nee, maar jouw methode houdt wel in dat je op gigantisch veel plekken in je applicatie herhaaldelijke en overbodige code gaat neer plempen. Je hebt producten die besteld worden (en dus in aantal krimpen), beheermodules waar producten toegevoegd en verwijderd kunnen worden, en tig andere situaties die de aantallen in kwestie beïnvloeden en waar jij dus in je broncode stukjes voor moet gaan plaatsen om die aantallen bij te houden. Nog even afgezien van het feit dat DBA`ers 'in geval van nood' (recovery) of uit pure gemakszucht ook nog wel eens zo je database in gaan om e.e.a. aan te passen, buiten de applicatie om. Ja, je kunt een knopje maken waarmee je wederom wéér letterlijk alles na moet gaan lopen (dus ook de rubrieken die niet ter sprake zijn) en berekenen, maar da's ook niet echt lekker voor daadwerkelijk actuele cijfers (want hoe vaak moet jij deze zware functie niet gaan uitvoeren om je cijfers daadwerlelijk actueel te houden?quote:Op woensdag 25 maart 2009 17:47 schreef GlowMouse het volgende:
Mooie code is niet altijd het criterium.
1 2 3 | $fp = fopen ("online/room101.txt","r+"); ?> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 | <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title>online</title> <META HTTP-EQUIV="refresh" CONTENT="5"> </head> <body> <? //simple user's online script $ip = $_SERVER['REMOTE_ADDR']; $time = time(); $cutoff = 15; //online cut of time $exists = 0; $users = 0; $user = ""; $fp = fopen ("online/room$_GET['room'].txt","r+"); //if the file exists open it while (!feof($fp)) { $user[] = chop(fgets($fp,65536)); } fseek($fp,0,SEEK_SET); foreach ($user as $line) { list($oldip,$oldtime) = explode('|',$line); if ($oldip == $ip) {$oldtime = $time;$exists = 1;} //check to see if the user is already in the text file if ($time < $oldtime + ($cutoff * 60)) //see if the last time the user visited is past the cut off time { fputs($fp,"$oldip|$oldtime\n"); //write the old data to the text file $users = $users + 1; // add one to the user count } } if ($exists == 0) //if the user isn't in the text file already: { fputs($fp,"$ip|$time\n"); //write the new data to the text file $users = $users + 1; //add one to the user count } fclose ($fp); //close the text file print "$users"; //display the number of users online ?> </body> </html> |
quote:
YES het werktquote:Op woensdag 25 maart 2009 20:46 schreef Roy_T het volgende:
Je code is zo insecure als de pest, maar { en } om $_GET['room'] lost het op
Het is in principe mogelijk met dat script iedere willekeurige tekstfile te lezen. (Het besturingssysteem kan nog wel beperkingen opleggen, maar iemand anders kan die rechten ook weer aanpassen. Daar moet je dus niet op vertrouwen.)quote:Op woensdag 25 maart 2009 20:53 schreef bassiedekloon het volgende:
[..]
YES het werkt![]()
Thnx voor de snelle reactie, maar hoe bedoel je insecure?
Ik hoef daar toch alleen rekening mee te houden als ik een database gebruik?
Die gebruik ik nog niet omdat ik nog niet weet hoe.
Kan. Maar fopen() geeft ook gewoon false terug als het bestand niet bestaat.quote:Op woensdag 25 maart 2009 22:02 schreef Catch22- het volgende:
eerst ff een file_exists op de gevraagde filename doen dus
@ voor de functie aanroep,niet echt een nette oplossing,maar het kan...quote:Op woensdag 25 maart 2009 22:07 schreef Light het volgende:
[..]
Kan. Maar fopen() geeft ook gewoon false terug als het bestand niet bestaat.
1 2 | { spul } |
Ik zal deze vandaag eens testenquote:Op woensdag 25 maart 2009 14:24 schreef slacker_nl het volgende:
Beetje simpele variant, kan volgens mij wel mooier:
[ code verwijderd ]
Ok, cool, werkt goed, maar nu wil ik mijn zoekopdracht meer specificeren, dus: mensen die gespecialiseerd zijn in operating system windows of mac en in programming language PHP of ASP.quote:Op dinsdag 24 maart 2009 16:22 schreef Tuvai.net het volgende:
Voorbeeldje om namen op te halen van mensen die gespecialiseerd zijn in OperatingSystem Windows:
[ code verwijderd ]
OF
[ code verwijderd ]
Kort samengevat: Met een LEFT OUTER JOIN ga je vanuit de 'diepere' tabel werken, met RIGHT OUTER JOIN ga je vanuit de bovenliggende tabel werken. Voor de rest is het in jouw geval simpelweg met de WHERE clausule spelen om de goede filtering toe te passen.
1 2 3 4 5 6 7 8 9 10 11 12 | w.name FROM werknemer w RIGHT OUTER JOIN specialiteiten s ON s.werknemer_id = w.id WHERE s.specialiteit_naam = 'OperatingSystems' AND s.waarde IN ('MAC', 'Windows') AND s.specialiteit_naam = 'ProgrammingLanguage' AND s.waarde IN ('PHP', 'ASP') ; |
Dan zul je toch e.e.a. met de WHERE clausule moeten goochelen, je statements met AND / OR aanvullen en eventueel in aparte 'blokjes' zetten, voorbeeld:quote:Op donderdag 26 maart 2009 10:27 schreef markiemark het volgende:
[..]
Ok, cool, werkt goed, maar nu wil ik mijn zoekopdracht meer specificeren, dus: mensen die gespecialiseerd zijn in operating system windows of mac en in programming language PHP of ASP.
[ code verwijderd ]
Hoe doe ik dat dan?
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 | w.name FROM werknemer w RIGHT OUTER JOIN specialiteiten s ON s.werknemer_id = w.id WHERE ( s.specialiteit_naam = 'OperatingSystems' AND ( s.waarde = 'MAC' OR s.waarde = 'Windows' ) ) AND ( s.specialiteit_naam = 'ProgrammingLanguage' AND ( s.waarde = 'PHP' OR s.waarde = 'ASP' ) ) |
quote:Op donderdag 26 maart 2009 10:52 schreef Tuvai.net het volgende:
[..]
Dan zul je toch e.e.a. met de WHERE clausule moeten goochelen, je statements met AND / OR aanvullen en eventueel in aparte 'blokjes' zetten, voorbeeld:
[ code verwijderd ]
1 2 3 4 5 6 7 8 9 10 11 12 | w.name FROM werknemer w RIGHT OUTER JOIN specialiteiten s ON s.werknemer_id = w.id WHERE ( s.specialiteit_naam = 'OperatingSystems' AND ( s.waarde = 'MAC' OR s.waarde = 'Windows' ) ) |
Kun je een tipje van de sluier oplichten wat betreft subqueries?quote:Op donderdag 26 maart 2009 11:27 schreef Tuvai.net het volgende:
EDIT: Ah klopt, ik had er even geen rekening mee gehouden dat het over een one-to-many tabel ging.Je selecteert in dit geval immers elke keer een losse 'specialiteiten' record. Je zult vrees ik toch e.e.a. met subqueries moeten doen.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | w.naam FROM werknemer w WHERE ( SELECT COUNT(*) FROM specialiteiten s WHERE s.werknemer_id = w.id AND s.specialiteit_naam = 'OperatingSystems' AND s.waarde IN ('MAC', 'Windows') ) > 0 AND ( SELECT COUNT(*) FROM specialiteiten s WHERE s.werknemer_id = w.id AND s.specialiteit_naam = 'ProgrammingLanguages' AND s.waarde IN ('PHP', 'ASP') ) > 0 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | w.naam FROM werknemer w WHERE ( SELECT COUNT(*) FROM specialiteiten s WHERE s.werknemer_id = w.id AND ( (s.specialiteit_naam = 'OperatingSystems' AND s.waarde IN ('MAC', 'Windows')) OR (s.specialiteit_naam = 'ProgrammingLanguages' AND s.waarde IN ('PHP', 'ASP')) ) ) = 2 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | <FORM METHOD="post" ACTION="mail.php"> <INPUT TYPE="hidden" NAME="to" VALUE="naam@domein.com"> <p> <INPUT TYPE="hidden" NAME="subject" VALUE="Voorbeeldformulier Handleiding HTML"> <strong>Naam*:</strong> <br><INPUT NAME="name" SIZE="45"> <br><strong>E-mail adres*:</strong> <br><INPUT NAME="email" SIZE="45"> <br><strong>Telefoonnummer*:</strong> <br><INPUT NAME="phone" SIZE="45"> <br><strong>Bericht/vraag:</strong> <br><INPUT TYPE="hidden" NAME="required_fields" VALUE="name, from, phone"> <TEXTAREA NAME="message" ROWS="3" COLS="45"></TEXTAREA> <br> <img class="rde_img_smiley" src="http://i.fok.nl/s/shiny.gif" width="15" height="15" alt="" /> svp invullen <br><br> <INPUT TYPE="reset" VALUE="Verwijder invoer"> <INPUT TYPE="submit" VALUE="Verzend gegevens"> </p> </FORM> ?> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | $name=$_POST['name']; $email=$_POST['email']; $phone=$_POST['phone']; $message=$_POST['message']; $ToEmail = "naam@domein.com"; $ToSubject = "Contact Form from domein.com"; $EmailBody = "Name: $name\n Email: $email\n Phone: $phone\n Message: $message\n"; $Message = $EmailBody; $headers .= "Content-type: text; charset=iso-8859-1\r\n"; $headers .= "From:".$email."\r\n"; mail($ToEmail,$ToSubject,$Message, $headers); header( "Location: contact2.html" ); ?> |
EDIT: snap hem al...quote:Op donderdag 26 maart 2009 12:13 schreef SuperRembo het volgende:
Die kan je ook samenvoegen:
[ code verwijderd ]
Ik denk dat er niet veel regels zijn waarbij specialiteit_naam = 'OperatingSystems' en specialiteit_naam = 'ProgrammingLanguages' is.quote:Op donderdag 26 maart 2009 13:05 schreef markiemark het volgende:
[..]
Kan ik daar ook dit van maken?
[ code verwijderd ]
* AND ipv OR
Hehe nee ik snap hem al..quote:Op donderdag 26 maart 2009 13:26 schreef SuperRembo het volgende:
[..]
Ik denk dat er niet veel regels zijn waarbij specialiteit_naam = 'OperatingSystems' en specialiteit_naam = 'ProgrammingLanguages' is.
Ik heb hem gelimit op 5, en dat duurt 6 seconden... Hoe kan dat?quote:Op donderdag 26 maart 2009 13:27 schreef markiemark het volgende:
[..]
Hehe nee ik snap hem al..
Je geeft denk ik een goede oplossing voor mij, maar mijn mysql server lijkt het niet te slikken...
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 | function addWatermark($image, $opacity) { if (!imageistruecolor($image)) die('addWatermark: Input image should be true color.'); // Load watermark image $wmFileName = 'images/watermark.png'; $wm = imagecreatefrompng($wmFileName); if (!$wm) die('Watermark image not found. '.$wmFileName); if (!imageistruecolor($wm)) die('addWatermark: Watermark image should be true color.'); $wmWidth = imagesx($wm); $wmHeight = imagesy($wm); // Lower right corner, with padding $destX = imagesx($image) - $wmWidth - 5; $destY = imagesy($image) - $wmHeight - 5; // Copy watermark to image imagecopymerge($image, $wm, $destX, $destY, 0, 0, $wmWidth, $wmHeight, $opacity); //imagecopy($image, $wm, $destX, $destY, 0, 0, $wmWidth, $wmHeight); // Clean up imagedestroy($wm); } ?> |
imagecopymerge verneukt inderdaad al de 'bestaande' transparency in een PNG. Met http://nl2.php.net/manual/en/function.imagecopyresampled.php imagecopy schijnt het met wat omweggetjes mogelijk te zijn wat jij wil. Ik heb het zelf eerlijk gezegd ook nog nooit geprobeerd daar ik deze situatie nog nooit ben tegengekomen, maar als ik de reacties op beide pagina's lees is het wel degelijk mogelijk.quote:Op donderdag 26 maart 2009 15:50 schreef SuperRembo het volgende:
Ik heb ook eens een vraag
Ik heb een functie om een watermark aan een plaatje toe te voegen. Dat werkt op zich prima, alleen zou ik de opacity van de watermark makkelijk willen kunnen aanpassen.
[ code verwijderd ]
Het probleem is dat imagecopymerge alle transparatie uit het watermark plaatje zelf weggooit. Met imagecopy blijft die informatie wel behouden, maar dan kan ik er dus niets aan tweaken via php.
Forum Opties | |
---|---|
Forumhop: | |
Hop naar: |