Office Forum
www.Office-Loesung.de
Access :: Excel :: Outlook :: PowerPoint :: Word :: Office :: Wieder Online ---> provisorisches Office Forum <-
ByVal - ByRef
zurück: Leere Ordner löschen, aber nur leere weiter: Autofiltern, kopieren und neue Tabellenblätter anlegen Unbeantwortete Beiträge anzeigen
Neues Thema eröffnen   Neue Antwort erstellen     Status: Antwort Facebook-Likes Diese Seite Freunden empfehlen
Zu Browser-Favoriten hinzufügen
Autor Nachricht
Phelan XLPH
Fortgeschritten


Verfasst am:
23. März 2013, 16:38
Rufname: Phelan

ByVal - ByRef - ByVal - ByRef

Nach oben
       Version: Office 2010

Hallo,

kann mir jemand erklären warum 'strWinOrdner' den Pfad enthält,
obwohl über ByVal lpBuffer As String lediglich
der Wert übergeben wird?

Code:
Public Declare Function GetWindowsDirectory _
Lib "kernel32" Alias "GetWindowsDirectoryA" ( _
ByVal lpBuffer As String, _
ByVal nSize As Long) As Long

Public Function GetWinDir() As String
  Dim strWinOrdner  As String * 255
  Dim lngLaenge      As Long
'API-Funktion aufrufen:
  lngLaenge = GetWindowsDirectory(strWinOrdner, _
              Len(strWinOrdner))
  GetWinDir = Left(strWinOrdner, lngLaenge)
End Function

Sub Test_GetWinDir()
   MsgBox "Windows-Ordner: " & GetWinDir
End Sub



Das Phänomen hatte ich auch schon bei Übergabe einer LisBox
an eine Funktion mit ByVal. Warum funktioniert das?

_________________
Was vorstellbar ist, ist auch machbar. - Albert Einstein
Flotter Feger
Gast


Verfasst am:
23. März 2013, 18:47
Rufname:


AW: ByVal - ByRef - AW: ByVal - ByRef

Nach oben
       Version: Office 2010

Hallöchen Phelan,

mir wurde das mal - mädchentechnisch - so erklärt:

Mit 'Byval' wird der Variablen im Speicher ein fester, unveränderlicher, lokaler Bereich zugewiesen. In deinem Fall, ein Char-Array mit 255 Byte Länge. Die API-Function schreibt jetzt in den festen Speicherbereich einfach andere Bytes hinein, hierdurch wird die Lokalisierung des Speicherbereich nicht geändert, nur die Bytewerte - also die Füllung im Speicher - ändern sich. Somit kann die API einfach den lokalen Speicherbereich - jetzt mit veränderten Bytewerten - wieder zurückgeben.

Würde der String jetzt 'byRef' übergeben werden, könnte die API-Function den festen Bereich im Speicher nicht lokalisieren - es gäbe ja keinen, da nur ein Zeiger auf einen Bereich im Speicher übergeben wird und nicht der Bereich selbst - und etwas byteweise zu ändern, was es eigentlich physisch nicht gibt, ist etwas kompliziert. Wink

Lies dir auch mal das durch http://www.a-m-i.de/tips/strings/strings.php#basics

VG Sabina Wink
Phelan XLPH
Fortgeschritten


Verfasst am:
23. März 2013, 20:05
Rufname: Phelan

AW: ByVal - ByRef - AW: ByVal - ByRef

Nach oben
       Version: Office 2010

Hallo Sabina,

ich versteh das nicht so ganz.

Im Grunde ist es ganz einfach.

Auszug aus der Hilfe:
Zitat:
ByVal Optional. Legt fest, daß das Argument als Wert übergeben wird.
ByRef Optional. Legt fest, daß das Argument als Verweis übergeben wird. ByRef ist der Standardwert in Visual Basic.


Als Test:

Code:
Sub Test()
    Dim intX As Integer
    Dim intY As Integer
    Dim intZ As Integer
   
    intX = 11
    intY = 111
    intZ = 1111
   
    Call Sub_BYVAL(intX)
    Call Sub_BYREF(intY)
    Call Sub_BYREFoa(intZ)
   
    MsgBox "Test intX: " & intX
    MsgBox "Test intY: " & intY 'erfährt Änderung
    MsgBox "Test intZ: " & intZ 'erfährt Änderung (Standardwert: ByRef)
End Sub

Sub Sub_BYVAL(ByVal x)
    x = x * 2
    MsgBox "Sub_BYVAL: " & x
End Sub

Sub Sub_BYREF(ByRef y)
    y = y * 2
    MsgBox "Sub_BYREF: " & y
End Sub

Sub Sub_BYREFoa(z)
    z = z * 2
    MsgBox "Sub_BYREF (ohne Angabe): " & z
End Sub


Ist doch recht einfach zu verstehen und der Testcode beweist es.

Warum es sich in manchen Fällen trotzdem so verhält, ist mir ein Rätsel. Confused

Weiß sonst noch jemand was darüber.

_________________
Was vorstellbar ist, ist auch machbar. - Albert Einstein
Isabelle :-)
Menschin


Verfasst am:
24. März 2013, 00:08
Rufname:
Wohnort: Westlicher Spiralarm der Galaxis

AW: ByVal - ByRef - AW: ByVal - ByRef

Nach oben
       Version: Office 2010

Hallöchen,

ByVal und ByRef in API-Aufrufen darfst du nicht mit denen von Prozeduraufrufen in VBA vergleichen.

Strings in API's werden immer als Referenz übergeben. Genauso wie Objekte in VBA. Wenn du z.B. eine Tabelle ByVal übergibst, kommt nicht etwa nur der Name der Tabelle an wie zu vermuten wäre, sondern trotzdem ein Verweis auf die Tabelle.

ByVal für Strings in API's konvertiert den VBA-String in einen Null-terminierten String (ein Char-Array mit ein 0-Char nach dem letzten Zeichen im String). Die Funktion schreibt in dieses Char-Array zurück.

ByRef übergibt den Pointer auf den String selbst.

Im Buch von Dan Appleman hab ich folgende Darstellung gefunden:

_________________
LG Isi

Die Mitgliedschaft im Forum erhöht deine Chance auf eine Antwort von mir um 99,999%



Buchauszug.jpg
 Beschreibung:
 Dateigröße:  25.65 KB
 Angeschaut:  288 mal

Buchauszug.jpg


Phelan XLPH
Fortgeschritten


Verfasst am:
24. März 2013, 10:44
Rufname: Phelan

AW: ByVal - ByRef - AW: ByVal - ByRef

Nach oben
       Version: Office 2010

Danke Isi,

das hier bestätigt meine Annahme:
Code:
ByVal und ByRef in API-Aufrufen darfst du nicht mit denen von Prozeduraufrufen in VBA vergleichen.

Strings in API's werden [u]immer als Referenz übergeben[/u]. Genauso wie Objekte in VBA. Wenn du z.B. eine Tabelle ByVal übergibst, kommt nicht etwa nur der Name der Tabelle an wie zu vermuten wäre, sondern trotzdem ein Verweis auf die Tabelle.


Zusammengefasst (so wie ich es mal gelernt hab):

ByRef: Verweis auf eine Speicherplatz-Adresse (wie der Name es schon sagt: Reference)
ByVal: Kopie in eine neue Speicherplatz-Adresse.

ByRef ist die schnellere Variante, steht iwo in der VBA-Hilfe.

Warum wird empfohlen Variablen einfacher Datentypen per byVal zu übergeben?
Zur Vermeidung von logischen Fehlern?

Ausserdem hätte ich jetzt erwartet, dass der Debugger in Kraft tritt, wenn ich
eine ListBox mit ByVal an eine Funktion übergebe, macht er aber nicht.

_________________
Was vorstellbar ist, ist auch machbar. - Albert Einstein
Isabelle :-)
Menschin


Verfasst am:
24. März 2013, 11:44
Rufname:
Wohnort: Westlicher Spiralarm der Galaxis

AW: ByVal - ByRef - AW: ByVal - ByRef

Nach oben
       Version: Office 2010

Hallöchen,

ich übergebe nur dann einfache Variable ByRef wenn, wenn ich sie explizit geändert an die aufrufende Prozedur zurückgeben will.

ByVal dauert zwar knapp 6mal so lange (0,6 Sekunden statt 0,1 Sekunden bei 10 Parametern und 1.000.000 Aufrufen Shock ) aber das nehme ich in Kauf.

Zitat:
Außerdem hätte ich jetzt erwartet, dass der Debugger in Kraft tritt


Einer der vielen Automatismen in VBA. Rolling Eyes

_________________
LG Isi

Die Mitgliedschaft im Forum erhöht deine Chance auf eine Antwort von mir um 99,999%
Phelan XLPH
Fortgeschritten


Verfasst am:
24. März 2013, 13:02
Rufname: Phelan

AW: ByVal - ByRef - AW: ByVal - ByRef

Nach oben
       Version: Office 2010

Hallo,

Zitat:
ByVal dauert zwar knapp 6mal so lange (0,6 Sekunden statt 0,1 Sekunden bei 10 Parametern und 1.000.000 Aufrufen ) aber das nehme ich in Kauf.


Wenn es ein 2dim-Array (Variant) ist, gefüllt mit Blattdaten, könnte eine Übergabe mit ByRef Vorteile bringen.

Naja, hängt vom Datenvolumen ab.

_________________
Was vorstellbar ist, ist auch machbar. - Albert Einstein
slowboarder
Im Profil kannst Du frei den Rang ändern


Verfasst am:
24. März 2013, 17:09
Rufname:


AW: ByVal - ByRef - AW: ByVal - ByRef

Nach oben
       Version: Office 2010

HI

byRef ist auch sehr streng bezüglich des Variablentyps.
Variablentyp der aufnehmenden und der übergebenen Variable müssen übereinstimmen.

bei byVal hingegen findet wen möglich eine Typumwandlung statt, so daß du sogar einen StringVariable übergeben kannst , wenn ein Double-Wert erwartet wird (natürlich nur, wenn sich dieser String in eine Zahl umwandeln lässt)

Gruß Daniel
Neues Thema eröffnen   Neue Antwort erstellen Alle Zeiten sind
GMT + 1 Stunde

Diese Seite Freunden empfehlen

Seite 1 von 1
Gehe zu:  
Du kannst Beiträge in dieses Forum schreiben.
Du kannst auf Beiträge in diesem Forum antworten.
Du kannst deine Beiträge in diesem Forum nicht bearbeiten.
Du kannst deine Beiträge in diesem Forum nicht löschen.
Du kannst an Umfragen in diesem Forum nicht mitmachen.
Du kannst Dateien in diesem Forum nicht posten
Du kannst Dateien in diesem Forum herunterladen

Verwandte Themen
Forum / Themen   Antworten   Autor   Aufrufe   Letzter Beitrag 
Keine neuen Beiträge Excel VBA (Makros): "Fehler beim kompilieren: Argumenttyp ByRef unverträgli 4 4treyu 86 22. Okt 2013, 21:55
4treyu "Fehler beim kompilieren: Argumenttyp ByRef unverträgli
Keine neuen Beiträge Excel VBA (Makros): Erst wenn Textlengh > 2 soll Change(ByVal Target As Excel 3 P4 85 10. Apr 2013, 12:15
P4 Erst wenn Textlengh > 2 soll Change(ByVal Target As Excel
Keine neuen Beiträge Excel VBA (Makros): ByVal Funktion nach Änderung durch Makro umgehen 2 Cribbi 72 19. März 2013, 11:13
Cribbi ByVal Funktion nach Änderung durch Makro umgehen
Keine neuen Beiträge Excel VBA (Makros): Argumenttyp ByRef unverträglich 7 andipalamos 297 22. Okt 2012, 16:17
slowboarder Argumenttyp ByRef unverträglich
Keine neuen Beiträge Excel VBA (Makros): Cancel "Worksheet_FollowHyperlink(ByVal Target As Hyper 0 Kieni 174 20. Sep 2012, 13:51
Kieni Cancel "Worksheet_FollowHyperlink(ByVal Target As Hyper
Keine neuen Beiträge Excel VBA (Makros): Private Sub Worksheet_Change(ByVal Target As Range) 5 DRH 379 17. Sep 2012, 14:19
rogstar Private Sub Worksheet_Change(ByVal Target As Range)
Keine neuen Beiträge Excel VBA (Makros): Privat Sub Worksheed_Change (ByVal...) mit mehreren Argument 2 PeacemanKGH 274 05. Apr 2012, 14:33
Gast Privat Sub Worksheed_Change (ByVal...) mit mehreren Argument
Keine neuen Beiträge Excel VBA (Makros): Worksheet_Change(ByVal Target As Range) funktioniert nicht 2 Praktikant99 507 16. Aug 2011, 17:06
Praktikant99 Worksheet_Change(ByVal Target As Range) funktioniert nicht
Keine neuen Beiträge Excel VBA (Makros): Probleme mit Makro ByVal Target As Range 2 Lupo_12_67 785 03. Jun 2011, 17:05
Lupo_12_67 Probleme mit Makro ByVal Target As Range
Keine neuen Beiträge Excel VBA (Makros): Worksheet_Change(ByVal Target As Range) - Ereignis 6 grille 1515 22. Jun 2010, 14:44
grille Worksheet_Change(ByVal Target As Range) - Ereignis
Keine neuen Beiträge Excel VBA (Makros): 2x Public Sub Worksheet_Change(ByVal Target As Range)???? 8 Gast 1515 08. Feb 2010, 17:42
Gast 2x  Public Sub Worksheet_Change(ByVal Target As Range)????
Keine neuen Beiträge Excel VBA (Makros): DDE und Private Sub Worksheet_Change(ByVal Target As Range) 3 Bolfo 2004 22. Apr 2009, 16:05
Bolfo DDE und Private Sub Worksheet_Change(ByVal Target As Range)
 

----> Diese Seite Freunden empfehlen <------ Impressum - Besuchen Sie auch: CSS Forum