Schrift
Wiki:Tipp zum Debugging: use Data::Dumper; local $Data::Dumper::Useqq = 1; print Dumper \@var;
[thread]11217[/thread]

array wird falsch/nicht belegt....



<< |< 1 2 >| >> 13 Einträge, 2 Seiten
Gast Gast
 2008-01-30 17:55
#105364 #105364
Hi!

Ich soll ein Skript schreiben, welches Daten aus einer Datei einlesen soll und diese Daten anschließend splittet und in ein Array schreibt.
Anschließend sollen aus einer bestimmte Spalte dieses Arrays die doppelten einträge "rausgefiltert" werden...

Das Filtern an sich klappt auch ganz gut...wenn ich aber die rausgefilterten Daten in ein 2. Array schreiben und ausgeben will, funktioniert das nicht.
Bei der anschließenden Ausgabe des 2. Arrays wird mir immer nur das letzte Element angezeigt.

Ich hab hier mal den Code reinkopiert...vielleicht erkennt ja jemand nen Fehler darin
Code (perl): (dl )
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
#!/usr/bin/perl

open (TEXTDAT, "<test_datei") or die $!;
@array = <TEXTDAT>;
$anzahl_saetze = $#array;
$x = 5;
$merker = "";
@array_neu_2 = undef;
while ($x<=$anzahl_saetze)
{
  @array_neu = split(/!/, $array[$x]);
  $anstaendiger_zaehler = $x+1;
  $elemente = $#{@array_neu};
  $y = 0;
  while ($y<=$elemente)
  {
  if ($y==1)
    {
      $hits = 0;
      $z = 1;
      if ($merker != $array_neu[$z])
       {
        $merker = $array_neu[$z];
       # $array_neu_2[$hits] =  $merker;
      # print "$array_neu_2[$hits]\n";
        $hits++;
@array_neu_2 = $merker;
       }
    }
 $y++;
  }
  $x++;
}
print "@array_neu_2\n"


Vielen Dank schonmal im Voraus für eure Antworten
nepos
 2008-01-31 09:34
#105370 #105370
User since
2005-08-17
1420 Artikel
BenutzerIn
[Homepage] [default_avatar]
Kann es sein, dass du in Zeile 27 eigentlich sowas willst:
Code (perl): (dl )
push(@array_neu2, $merker);
Struppi
 2008-01-31 12:50
#105377 #105377
User since
2006-02-17
628 Artikel
BenutzerIn
[Homepage]
user image
Ausserdem läßt sich sowas mit Perl viel einfacher ohne irgendwelche Zähler bewerkstelligen. In etwa so:
Code (perl): (dl )
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#!/usr/bin/perl -w
use strict;
open TEXTDAT, '<', "text.txt" or die $!;
<TEXTDAT> for 0..4;
my $merker = '';
my @array;
while( <TEXTDAT> ) {
        chomp;
        my @daten = split /!/, $_;
        if($merker != $daten[1]) {
                $merker = $daten[1];
                $hits++;
                push @array, $merker;
        }
        
}
close TEXTDAT;
Wobei ich die innere Schleife bei dir nicht verstanden habe, deshalb kommt sie hier nicht vor.

Und du solltest dir dringend use strict angwöhnen
#Kein Kommentar
 2008-01-31 13:30
#105381 #105381
User since
2007-06-09
575 Artikel
HausmeisterIn
[default_avatar]
Struppi+2008-01-31 11:50:23--
Code (perl): (dl )
<TEXTDAT> for 0..4;


was macht denn diese zeile?
öffnet die viermal das filehandle, aber wozu?
Gerade weil wir alle in einem Boot sitzen, sollten wir froh sein, dass nicht alle auf unserer Seite sind
Strat
 2008-01-31 13:55
#105386 #105386
User since
2003-08-04
5246 Artikel
ModeratorIn
[Homepage] [default_avatar]
Struppi+2008-01-31 11:50:23--
Code (perl): (dl )
while( <TEXTDAT> ) {


diese Schreibweise kann zu schwierig zu findenden Fehlern führen, weil da das globale $_ verändert wird (im Gegensatz zu foreach (<TEXTDAT>), was einen Alias verwendet). Deshalb da immer einen "Laufvariable" verwenden:

Code (perl): (dl )
1
2
3
4
5
6
7
8
9
10
while( my $line = <TEXTDAT> ) {
        chomp $line;
        my @daten = split( /!/, $line );
        if($merker != $daten[1]) {
                $merker = $daten[1];
                $hits++;
                push @array, $merker;
        }
        
}

Besser noch lokale filehandles verwenden, z.B.

Code (perl): (dl )
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
#!/usr/bin/perl
use strict;
use warnings; # besser als -w, weil es nur die aktuelle Datei betrifft

my $file = "text.txt";
open( my $TEXTDAT, '<', $file ) or die "Error: couldn't open file '$file': $!";
<$TEXTDAT> for 0..4; # ok, weil for bei $_ einen alias auf den Wert enthält, der nach ende der Schleife "wiederhergestellt" wird.
my $merker = '';
my @array;
while( my $line = <$TEXTDAT> ) {
        chomp $line;
        my @daten = split( /!/, $line );
        if($merker != $daten[1]) {
            $merker = $daten[1];
            $hits++;
            push @array, $merker;
        }
        
}
close $TEXTDAT;
perl -le "s::*erlco'unaty.'.dk':e,y;*kn:ai;penmic;;print"
http://www.fabiani.net/
Linuxer
 2008-01-31 14:16
#105389 #105389
User since
2006-01-27
3891 Artikel
HausmeisterIn

user image
#Kein Kommentar+2008-01-31 12:30:05--
Struppi+2008-01-31 11:50:23--
Code (perl): (dl )
<TEXTDAT> for 0..4;


was macht denn diese zeile?
öffnet die viermal das filehandle, aber wozu?


Es wird 5mal (0,1,2,3,4 = 5x) vom Filehandle gelesen.
Das ist quasi ein Ignorieren der ersten 5 Zeilen.

Könnte man auch so lösen:
Code (perl): (dl )
1
2
3
4
5
6
while ( my $line = <$handle> ){
    # ignoriere die ersten 5 "Zeilen"
    next if ( $. <= 5 );
    chomp $line;
    # ...
}

Wobei hierbei die Prüfung ( $. <= 5 ) bei *jeder* Zeile vollzogen werden muss. Ob das "besser" ist, dürfen andere entscheiden ;o)
meine Beiträge: I.d.R. alle Angaben ohne Gewähr und auf Linux abgestimmt!
Die Sprache heisst Perl, nicht PERL. - Bitte Crossposts als solche kenntlich machen!
renee
 2008-01-31 14:17
#105391 #105391
User since
2003-08-04
14371 Artikel
ModeratorIn
[Homepage] [default_avatar]
#Kein Kommentar+2008-01-31 12:30:05--
Struppi+2008-01-31 11:50:23--
Code (perl): (dl )
<TEXTDAT> for 0..4;


was macht denn diese zeile?
öffnet die viermal das filehandle, aber wozu?


Das öffnet nicht das Filehandle, sondern es liest 5 Zeilen aus... Dieser Code entspricht:

Code (perl): (dl )
1
2
3
for(0..4){
  <TEXTDAT>
}


Edit: Die ausgelesene Zeile wird halt keiner Variablen zugewiesen. Du wirst sicherlich so etwas kennen:

my $zeile = <TEXTDAT>

Hier wird halt die Zuweisung weggelassen, weil die ersten 5 Zeilen uninteressant sind.
OTRS-Erweiterungen (http://feature-addons.de/)
Frankfurt Perlmongers (http://frankfurt.pm/)
--

Unterlagen OTRS-Workshop 2012: http://otrs.perl-services.de/workshop.html
Perl-Entwicklung: http://perl-services.de/
Struppi
 2008-01-31 14:20
#105392 #105392
User since
2006-02-17
628 Artikel
BenutzerIn
[Homepage]
user image
Wie immer gibt es tausend Möglichkeiten, aber jede ist beeser als das Orginal.
#Kein Kommentar+2008-01-31 12:30:05--
Struppi+2008-01-31 11:50:23--
Code (perl): (dl )
<TEXTDAT> for 0..4;
was macht denn diese zeile?
öffnet die viermal das filehandle, aber wozu?

Wieso öffnen? Das ist das was das Orginalskript auch tun soll, der OP will ja die ersten 4 Zeilen überlesen
#Kein Kommentar
 2008-01-31 14:25
#105394 #105394
User since
2007-06-09
575 Artikel
HausmeisterIn
[default_avatar]
sorry hatte garnet so weit gedacht... bei meinen dateien sind immer alle zeilen
wichtig :) ... ah, sowieso 0..4 ist fünfmal und nich viermal....
Gerade weil wir alle in einem Boot sitzen, sollten wir froh sein, dass nicht alle auf unserer Seite sind
Gast Gast
 2008-02-01 10:21
#105433 #105433
Danke erstmal für eure schnellen Antworten!!

nepos+2008-01-31 08:34:26--
Kann es sein, dass du in Zeile 27 eigentlich sowas willst:
Code (perl): (dl )
push(@array_neu2, $merker);


Ja das war mein Fehler...hab das "push" vergessen....
Jetzt klappt es...zumindest bis zu einem bestimmten Punkt.

Ich hab jetzt erstmal das Skript von @Struppi übernommen weil es doch viel übersichtlicher ist;)

Allerdings taucht bei beiden Varianten, also meiner und Struppi's, das gleiche Problem auf....
Die Zeilen der Spalte, die ich filtern möchte, beinhalten zum Anfang nur Zahlenkombinationen, aber irgendwann beginnt der Zeileninhalt nur noch mit Buchstaben.
Die beiden Skripte brechen jeweils in dem Moment ab, in dem die erste Buchstabenkombination auftaucht....

Ist es überhaupt möglich, so eine "gemischte" Spalte zu filtern?
Oder gibt's da nur Probleme mit?
<< |< 1 2 >| >> 13 Einträge, 2 Seiten



View all threads created 2008-01-30 17:55.