Schrift
[thread]6341[/thread]

abgedrehtes problem mit switch: oder bin ich blind? (Seite 6)



<< |< 1 ... 3 4 5 6 7 8 >| >> 72 Einträge, 8 Seiten
Gast Gast
 2004-07-06 12:45
#83480 #83480
[quote=pq,05.07.2004, 19:26][quote=ptk,05.07.2004, 18:54]
Natuerlich kann man in einem BEGIN-Block auch auf globale Variablen zugreifen:[/quote]
sogar auf lexikalische:
Code: (dl )
1
2
3
4
5
my $x;
BEGIN {
 $x = 1234;
}
warn $x;
[/quote]
Dabei greift das Hauptprogramm auf eine Variable des BEGIN Blocks zu - und nicht umgekehrt.
Crian
 2004-07-07 04:19
#83481 #83481
User since
2003-08-04
5873 Artikel
ModeratorIn
[Homepage]
user image
[quote=ptk,05.07.2004, 18:54]Es ist hoechstens etwas irritierend, wenn man
Code: (dl )
1
2
3
4
$xxx = 1234;
BEGIN {
   warn $xxx;
}

schreibt und nicht das erwartete Ergebnis bekommt.[/quote]
Ja, das meinte ich.
s--Pevna-;s.([a-z]).chr((ord($1)-84)%26+97).gee; s^([A-Z])^chr((ord($1)-52)%26+65)^gee;print;

use strict; use warnings; Link zu meiner Perlseite
pq
 2004-07-07 12:31
#83482 #83482
User since
2003-08-04
12209 Artikel
Admin1
[Homepage]
user image
[quote=Dieter,06.07.2004, 10:45]
Dabei greift das Hauptprogramm auf eine Variable des BEGIN Blocks zu - und nicht umgekehrt.[/quote]
sehe ich anders.
Always code as if the guy who ends up maintaining your code will be a violent psychopath who knows where you live. -- Damian Conway in "Perl Best Practices"
lesen: Wiki:Wie frage ich & perlintro Wiki:brian's Leitfaden für jedes Perl-Problem
kabel
 2004-07-07 15:23
#83483 #83483
User since
2003-08-04
704 Artikel
BenutzerIn
[default_avatar]
[quote=Dieter,06.07.2004, 10:45]Dabei greift das Hauptprogramm auf eine Variable des BEGIN Blocks zu - und nicht umgekehrt.[/quote]
@dieter: erkläre dieses satz so, als ob hier nur dummies ohne gehirn rumposten würden.
im speziellen interessiert mich die frage, ob im betreffenden BEGIN block überhaupt variablen erzeugt werden, auf die man zugreifen könnte.

edit: also was haben wir hier jetzt: perl, grundlagen, mod_perl, apache ... gleich haben wir alles in EINEM thread! 8)\n\n

<!--EDIT|kabel|1089199482-->
-- stefan
Gast Gast
 2004-07-07 16:55
#83484 #83484
[quote=kabel,07.07.2004, 13:23][quote=Dieter,06.07.2004, 10:45]Dabei greift das Hauptprogramm auf eine Variable des BEGIN Blocks zu - und nicht umgekehrt.[/quote]
@dieter: erkläre dieses satz so, als ob hier nur dummies ohne gehirn rumposten würden.
im speziellen interessiert mich die frage, ob im betreffenden BEGIN block überhaupt variablen erzeugt werden, auf die man zugreifen könnte.

edit: also was haben wir hier jetzt: perl, grundlagen, mod_perl, apache ... gleich haben wir alles in EINEM thread! 8)[/quote]
- Ein BEGIN Block ist 'immer' die 'erste Tat' des Compilers
- Ein BEGIN Block wird compiliert und ausgeführt, noch 'bevor' sich der Compiler um den Rest des Programms kümmert

Ergo:
Zum Ausführungszeitpunkt des BEGIN Blocks sind dem Compiler (und damit dem Block) die Inhalte des Hauptprogramms (noch) nicht bekannt, daher ist es dem Block nicht möglich, auf Variablen des Hauptprogramms zuzugreifen

- Variablen die innerhalb des BEGIN Blocks mit 'my' deklariert sind, werden vom Hauptprogramm 'nicht' gesehen
- Variablen die innerhalb des BEGIN Blocks mit 'our' deklariert sind, werden vom Hauptprogramm gesehen
- Variablen die innerhalb des BEGIN Blocks nicht deklariert werden, sind automatisch 'global' und werden vom Hauptprogramm gesehen
- Sonder-Variablen, denen innerhalb des BEGIN Blocks eine Behandlung zukommt, werden vom Hauptprogramm gesehen

Die Beispiele von ptk und pq sollte man einmal unter 'use strict' laufen lassen - dann wird der dortige Gedankenfehler klarer ...
pq
 2004-07-07 17:23
#83485 #83485
User since
2003-08-04
12209 Artikel
Admin1
[Homepage]
user image
[quote=Dieter,07.07.2004, 14:55]
- Ein BEGIN Block ist 'immer' die 'erste Tat' des Compilers
- Ein BEGIN Block wird compiliert und ausgeführt, noch 'bevor' sich der Compiler um den Rest des Programms kümmert
[/quote]
perlmod.pod:A "BEGIN" subroutine is executed as soon as possible, that
is, the moment it is completely defined, even before the
rest of the containing file is parsed.

d.h. der teil des programms vor dem BEGIN wird geparsed. somit auch
ein my $x; vor dem BEGIN-block. siehe beispiel unten mit strict.
Quote
Ergo:
Zum Ausführungszeitpunkt des BEGIN Blocks sind dem Compiler (und damit dem Block) die Inhalte des Hauptprogramms (noch) nicht bekannt, daher ist es dem Block nicht möglich, auf Variablen des Hauptprogramms zuzugreifen

doch, der teil vor BEGIN ist bekannt. noch nicht ausgeführt, aber bekannt. dazu gehören deklarationen wie my(), our() etc.
Quote
- Variablen die innerhalb des BEGIN Blocks mit 'my' deklariert sind, werden vom Hauptprogramm 'nicht' gesehen

ok
Quote
- Variablen die innerhalb des BEGIN Blocks mit 'our' deklariert sind, werden vom Hauptprogramm gesehen

ja, wobei aber speziell
print $x;
BEGIN { our $x = 23; }

nicht unter strict läuft, weil das print vorher geparsed wird.
Quote
- Variablen die innerhalb des BEGIN Blocks nicht deklariert werden, sind automatisch 'global' und werden vom Hauptprogramm gesehen

was soll das heissen? du meinst also etwa
BEGIN { $x = 1234; }?
in dem fall ist $main::x gemeint, also global, richtig.
aber mit einem my $x; vorher ist es nicht mehr $main::x, also
nicht global, sondern lexikalisch.
hier der beweis:
Code: (dl )
1
2
3
4
5
6
7
8
9
10
tina@tuxedo:~> perl -wle'
my $x; # lexikalisch
BEGIN {
$x = 23;
$y = 42;
}
print "x: $main::x, y: $main::y"'
Name "main::x" used only once: possible typo at -e line 7.
Use of uninitialized value in concatenation (.) or string at -e line 7.
x: , y: 42

$y ist package-global, $x nicht.
Quote
Die Beispiele von ptk und pq sollte man einmal unter 'use strict' laufen lassen - dann wird der dortige Gedankenfehler klarer ...

bitte...
Code: (dl )
1
2
3
4
5
6
7
8
tina@tuxedo:~> perl -Mstrict -wle'
my $x;
BEGIN {
$x = 1234;
}
warn $x;'
1234 at -e line 6.
tina@tuxedo:~>
Always code as if the guy who ends up maintaining your code will be a violent psychopath who knows where you live. -- Damian Conway in "Perl Best Practices"
lesen: Wiki:Wie frage ich & perlintro Wiki:brian's Leitfaden für jedes Perl-Problem
Crian
 2004-07-07 17:25
#83486 #83486
User since
2003-08-04
5873 Artikel
ModeratorIn
[Homepage]
user image
(Als ich diesen Beitrag schrieb war pq's Beitrag noch nicht da, deshalb überschneidet sich dies...)

Interessant ist dieses:

Code: (dl )
1
2
3
4
5
6
7
8
9
10
11
12
13
#!/usr/bin/perl
use strict;
use warnings;

my $xxx = 1234;

BEGIN {
  warn $xxx;
  $xxx = 5678;
  warn $xxx;
}

warn $xxx;


Ausgabe:

Code: (dl )
1
2
3
4
Use of uninitialized value in warn at C:\Daten\perl\BEGIN.pl line 8.
Warning: something's wrong at C:\Daten\perl\BEGIN.pl line 8.
5678 at C:\Daten\perl\BEGIN.pl line 10.
1234 at C:\Daten\perl\BEGIN.pl line 13.



Ich erkläre mir das jetzt mal laienhaft so:

1) Deklaration der globalen im normalen Teil vor dem BEGIN wird interpretiert.

2) Der Code im BEGIN-Block wird interpretiert, dabei stößt Perl auf eine uninitialisierte unbekannte Variable.

3) Dann wird die Definition "= 1234" im normalen Code interpretiert.



Lässt man das Wort "BEGIN" weg, ist die Ausgabe diese:

Code: (dl )
1
2
3
1234 at C:\Daten\perl\BEGIN2.pl line 8.
5678 at C:\Daten\perl\BEGIN2.pl line 10.
5678 at C:\Daten\perl\BEGIN2.pl line 13.



Also: Möchte man lexikalische Variablen im BEGIN-Block definieren, so darf man sie außerhalb nur deklarieren, aber nicht definieren (also keinen Wert zuweisen), da dieser sonst die Initialisierung innerhalb des BEGIN-Blocks wieder überschreiben würde, da der Definitionsteil erst nach dem BEGIN-Block interpretiert wird:

Code: (dl )
1
2
3
4
#!/usr/bin/perl
use strict;
my $x; print $x;
BEGIN { $x = 'aha' }


Ausgabe: aha

Im Gegensatz zu

Code: (dl )
1
2
3
4
#!/usr/bin/perl
use strict;
my $x = 'NIX'; print $x;
BEGIN { $x = 'aha' }


welches NIXNIX ausgibt.

Alles ganz logisch, aber man muss es halt wissen, wie es funktioniert. Ich glaube ich habe es jetzt verstanden...\n\n

<!--EDIT|Crian|1089209158-->
s--Pevna-;s.([a-z]).chr((ord($1)-84)%26+97).gee; s^([A-Z])^chr((ord($1)-52)%26+65)^gee;print;

use strict; use warnings; Link zu meiner Perlseite
pq
 2004-07-07 17:29
#83487 #83487
User since
2003-08-04
12209 Artikel
Admin1
[Homepage]
user image
@crian: wieso?
beim ersten warn (im BEGIN) ist $x zwar deklariert, aber nicht initialisiert.
beim zweiten warn (auch im BEGIN) ist $x nun gesetzt, auf 5678. auch ok.
beim dritten warn, nun ausserhalb von BEGIN, wurde schließlich
my $xxx = 1234; ausgeführt, deswegen ist $x jetzt 1234.
also alles ganz logisch...
Always code as if the guy who ends up maintaining your code will be a violent psychopath who knows where you live. -- Damian Conway in "Perl Best Practices"
lesen: Wiki:Wie frage ich & perlintro Wiki:brian's Leitfaden für jedes Perl-Problem
Crian
 2004-07-07 17:36
#83488 #83488
User since
2003-08-04
5873 Artikel
ModeratorIn
[Homepage]
user image
ja danke, sowas ähnliches hatte ich mir auch gerade zurecht-überlegt (siehe veränderten Beitrag =)

@Dieter: Wo ist denn jetzt der von Dir angemeckerte "Gedankenfehler"?
s--Pevna-;s.([a-z]).chr((ord($1)-84)%26+97).gee; s^([A-Z])^chr((ord($1)-52)%26+65)^gee;print;

use strict; use warnings; Link zu meiner Perlseite
Gast Gast
 2004-07-07 17:39
#83489 #83489
@pq
Du kannst den BEGIN Block auch an das Ende des Scripts stellen.
Der Parser sucht zunächst einmal nach einem solchen Block/solchen Blöcken und ignoriert dabei alles was er 'vor' dem ersten BEGIN Block findet (so jedenfalls die einschlägige Literatur).
Der w.o.g. Link von Renee führt zu einem kleinen Beispiel-Script welches die Reihenfolge der Code-Ausführung sehr schön verdeutlicht.
<< |< 1 ... 3 4 5 6 7 8 >| >> 72 Einträge, 8 Seiten



View all threads created 2004-06-16 21:56.