Korbinian Bachl: DBI & Mysql .. ich raffs nicht...

Hi,

ich hab mich jetzt schon durch zig Tutorials gewühlt.. (unter anderem alle die bei SelfHTML gelinkt sind) aber wie ich daten aus einer DB auslese und dann DARSTELLE... das kapier ic bisher nicht ganz.. (zur verteidigung: ich komme aus dem PHP lager, bin also etwas andere umgangsarten mit DBs gewohnt):

hier der code:

#!/usr/bin/perl

use DBI;
use strict;

my $data_source = "dbi:mysql:DB";
my ($username,$password) = ("USER","PASS");

my $dbh = DBI->connect($data_source,$username,$password) || die "Keine Verbindung zum mySQL-Server: $DBI::errstr\n";

my $statement = "select * from sets";
my $sth = $dbh->prepare($statement) || die $dbh->errstr;
my $success = $sth->execute();

while (my ($bestnr) = $sth->fetchrow_array)
       {
        print $bestnr;
       }

$sth->finish;
$dbh->disconnect;

-> soweit so gut, doch statt der erhofften spalte bestnr bringt er mir nur wirre zahlen her... 12107342397192837193131289371297319237... was sol ich damit ? ... evtl. array ? aber ein $bestnr[$i] wobei $i++ war wurde von ihm abgeschmettert... bitte helft mir :O

  1. Hallo,

    my $dbh = DBI->connect($data_source,$username,$password) || die "Keine Verbindung zum mySQL-Server: $DBI::errstr\n";

    my $statement = "select * from sets";

    Wenn ich den Zusammenhang betrachte, wäre es besser, Du schreibst
      my $statement = "select bestnr from sets";
    (das ist jetzt aber unabhängig von der Programmiersprache. Es sollten sowieso nur jene Tabellenfelder abgefragt werden, die auch wirklich benötigt werden)

    my $sth = $dbh->prepare($statement) || die $dbh->errstr;
    my $success = $sth->execute();

    Auch hier eine Anregung: Du prüfst zwar den connect und das prepare aber beim execute nimmst Du jetzt an, daß es funktionierte. ABer auch das kann in die Hose gehen. Also solltest Du auch hier eine Fehlerbehandlung einbauen.

    while (my ($bestnr) = $sth->fetchrow_array)
           {
            print $bestnr;
           }

    -> soweit so gut, doch statt der erhofften spalte bestnr bringt er mir nur wirre zahlen her... 12107342397192837193131289371297319237 [...]

    Diese 'wirren Zahlen' sind einfach eine Aneinanderreihung  aller Bestellnummern, welche Du von der Datenbank erhalten hast.
    Das ist nähmlich das was Du mit
      print $bestnr;
    erreichst. Es werden einfach nur die Bestellnummern ausgegeben.
    Der Grund: Perl gibt standardmäßig beim print die übergebenen Werte (hier $bestnr) aus, und zwar ohne irgendeiner Formatierung.
    Willst Du beispielsweise jeden Wert in einer eigenen Zeile, dann kannst Du schreiben:

    while (my ($bestnr) = $sth->fetchrow_array)
           {
           print "$bestnr\n";
           }
    Was es mit den " und dem \n auf sich hat, kannst Du ja in der Perl-Dokumentation nachlesen (perldoc perlop, Kapitel 'Quote and Quote-like Operators').
    Und wie das genau mit dem print funktioniert findest Du unter (perldoc -f print)

    Grüße
      Klaus

    PS.: Ach ja, für die ganzen perldoc dinger verwendest Du am besten eine Command-shell. Unter Windows heißt das ganze Eingabeaufforderung. Und falls Du  unter Windows arbeitest und den PErl-Port von Activestate verwendest, gibt da auch noch die HTML-Dokumentation in der Du auch alles findest.

  2. Hallo !

    Ich habe schon längere Zeit nicht mehr mit Perl auf MySQL zugegriffen, aber wenn ich mich nicht völlig täusche, liefert $sth->fetchrow_array) in der Tat ein Array zurück, und zwar je nach den im SQL-Select-Statement angegebenen Datenbankfeldern.

    Ein direkter Zugriff auf die Arrayfelder mittels des Datenbankfeldnames, so wie du es versucht hast, ist IMHO mit DBI nicht möglich.

    Ein Beispiel zur Verdeutlichung:

    SQL-Statement: "SELECT vorname, nachname, strasse, ort FROM adressen"

    Ausgabe:

    while ( @namen = $sth->fetchrow_array ) {
        print "Vorname: @namen[0]\n";
        print "Nachname: @namen[1]\n";
        print "Strasse: @namen[2]\n";
        print "Ort: @namen[3]\n\n";
      }

    Bei SELECT * FROM adressen werden entsprechend _alle_ Felder des Datensatzes zurückgegeben. Generell ist es aber, wie Klaus auch schon sagte, besser, die DB-Feldnamen im SQL-Statement namentlich aufzuführen, sogar wenn du alle Felder des Datensatzes auslesen willst.

    Gruß,

    kerki

    1. Hallo, ich nochmal !

      Ich habe schon längere Zeit nicht mehr mit Perl auf MySQL zugegriffen

      Genau genommen, habe ich in letzter Zeit überhaupt nicht mehr mit Perl gearbeitet.

      Man merkt's. :-(((

      Das war wohl nichts:

      while ( @namen = $sth->fetchrow_array ) {
          print "Vorname: @namen[0]\n";
          print "Nachname: @namen[1]\n";
          print "Strasse: @namen[2]\n";
          print "Ort: @namen[3]\n\n";
        }

      Wenn überhaupt, wohl eher so:

      while ( @namen = $sth->fetchrow_array ) {
           print "Vorname: $namen[0]\n";
           print "Nachname: $namen[1]\n";
           print "Strasse: $namen[2]\n";
           print "Ort: $namen[3]\n\n";
         }

      Gruß,

      kerki

      1. Hallo,

        @kerki:

        Das war wohl nichts:

        while ( @namen = $sth->fetchrow_array ) {
            print "Vorname: @namen[0]\n";
        Wenn überhaupt, wohl eher so:
        while ( @namen = $sth->fetchrow_array ) {
             print "Vorname: $namen[0]\n";

        In neueren Perl-Versionen ist sowohl als auch möglich (Ich denke ab 5.6, aber sicher bin ich mir nicht)

        @Korbinian:
        Ich denke Deine Email-Antwort wäre hier als Posting besser angebracht gewesen. Ich will auch hier darauf heingehen:
        1.)Du meintest, in php hast Du immer 'select * from irgendwas' verwendet.
        Das geht natürlich auch mit Perl, da das ja eigentlich mehr mit der Datenbank zu tun hat als mit der verwendeten Programmiersprache.
        Warum es m.E. besser ist, 'select X,Y,Z from irgendwas' zu verwenden, hat unter anderem den Grund, daß sich beispielsweise die Datenstrukur irgendwie ändern kann, und Du dann vielleicht die Felder nicht in der angenommenen Weise erhältst.
        Außerdem wird beim betrachten des Codes klar, was da so daherkommt (Dein Beispiel mit $row[0] sagt mir absolut nicht, ob das z.B. ein Name oder eine ID ist, und Dir in 2 Monaten vielleciht auch nicht mehr )

        2.) in PHP machts folgendes:
        while ($row = mysql_fetch_array($query))
        { echo $row[spalte]; }
        Dabei ist $row anscheinen ein Array mit den Werten des Datensatzes.

        In Perl ersetzt Du das $ durch ein @ und das echo durch ein print.
        while ( @row = $sth->fetchrow_array ) {
          print @row[0];}

        oder
        while ( $row = $sth->fetchrow_hashref ) {
          print $row->{feld1};}

        oder

        while ( ($feld1,$feld2,$feld3( = $sth->fetchrow_array ) {
          print $feld1;}

        (wobei ich nicht weiß ob echo und print gleich reagieren, da kenn ich PHP zu wenig, sprich gar nicht)
        Es gibt in Perl viele Wege, die zum Ziel führen, vielleicht für den Einen oder Andern zu viele.

        Grüße
          Klaus