en varios codigos he visto que al momento de llamar a una funcion los parametros se pasan de manera distinta que la de su declaracion, si un `parametros esta como byref al llamar lo pasan como byval:
'en el parametro buffer esta sin nada (por ahi lei que si no se indica es ByRef por defecto)
Declare Function ReadProcessMemory Lib "kernel32" (ByVal hProcess As Long, ByVal lpBaseAddress As Any, lpBuffer As Any, ByVal nSize As Long, lpNumberOfBytesWritten As Long) As Long
'pasa el parametro buffer como byval
Dim Buffer As String
Buffer = Space(5000)
Call ReadProcessMemory(hProcess, Direccion, ByVal Buffer, Len(Buffer), BytesLeidos)
otra api:
'ambas apis son por valor
Private Declare Function FindWindow Lib "user32" _
Alias "FindWindowA" ( _
ByVal lpClassName As String, _
ByVal lpWindowName As String) As Long
'pasa el windowname - titulo sin nada (por defecto seria ByRef)
Dim Titulo As String
Titulo = "Google"
Call FindWindow(vbNullString, Titulo)
weno al final cual es el que vale? el ByVal/ByRef indicado en la declaracion de funcion o el ByVal/ByRef usado al momento de llamar a esa funcion?
si pudieran explicarme mejor esto del ByVal/ByRef se los agradeceria .
me lei :
http://foro.elhacker.net/programacion_vb/memoria_en_vb-t114052.0.html
no me kedo muy claro.
hola, byval es que a la funcion le pasas el valor te tu variable y lo procesas... y byref lo que procesas es la variable, supon que tienes una funcion fun y recibe 1 variable byref, normalmente si despues de invocar la función revisas que valor tiene v, no debería haber cambiado, pues byref si lo hace :P
dim v as string
fun(v)
msgbox v
http://foro.elhacker.net/programacion_visual_basic/byval_y_byref-t320592.0.html;msg1585427 (http://foro.elhacker.net/programacion_visual_basic/byval_y_byref-t320592.0.html;msg1585427) usa el buscador! :¬¬
Cita de: Tenient101 en 10 Julio 2011, 04:14 AM
http://foro.elhacker.net/programacion_visual_basic/byval_y_byref-t320592.0.html;msg1585427 (http://foro.elhacker.net/programacion_visual_basic/byval_y_byref-t320592.0.html;msg1585427) usa el buscador! :¬¬
:huh:
Citarweno al final cual es el que vale? el ByVal/ByRef indicado en la declaracion de funcion o el ByVal/ByRef usado al momento de llamar a esa funcion?
lo que dijo Nakp esta claro.
veo muchos codes que pasan parametros de manera distinta a como lo declaran, ejm: los codes que puse arriba (aqui la duda).
probe a ver q sale quitando los ByVal que tiene el FindWindow:
Private Declare Function FindWindow Lib "user32" Alias "FindWindowA" (lpClassName As String, ByVal lpWindowName As String) As Long
y pues no logra encontrar la ventana.
weno ahi nomas dejalo ps.
Cita de: alxspy en 10 Julio 2011, 22:32 PM
Cita de: Tenient101 en 10 Julio 2011, 04:14 AM
http://foro.elhacker.net/programacion_visual_basic/byval_y_byref-t320592.0.html;msg1585427 (http://foro.elhacker.net/programacion_visual_basic/byval_y_byref-t320592.0.html;msg1585427) usa el buscador! :¬¬
:huh:
En ese hilo (y en muchos mas buscando :P) explican porque el uso de ByVal y ByRef, en API la mayoria de las variables se pasan por punteros
as Any
no te lo recomiendo en vb6 esta bien pero en la practica es una mala practica, mejor declara TODO como punteros...
byval variable as long
Esto es por que al final practiamente Siempre se termina por obtener el puntero a la variable... ademas evita esos feos Crash que suelen ocurrir sin mera explicacion.
Dulces Lunas!¡.
.
ByVal y Byref esta explicado de alguna manera ante los procesos y funciones personalisados (en la liga y todos han ido directo a este punto mas no al real problema de este hilo, las apis.), es decir, las que creamos o las de vb6 mas no a las APIS, asi que aqui te dejo una explicacion ante esto.:
En las APIS byval y ByRef tienen otra tarea no muy alejada de la que ya se ha explicado, aun que yo recomiendo siempre trabajar con byval ya que al termino se trataran punteros y las referencias pasaran a ser un lobo en la piel de una oveja...
---------->
Puntero/Apuntador --> Es una variable que apunta a la dirrecion de memoria donde se encuentra una dato X.
Las apis no nesesitan crear una Copia de los texto ni nada similar, solo nesesitan el punto de inicio de los datos (puntero), y la longitudad a tratar...
Algunas apis piden referencia?... la referencia esta desde C++ ( en C no he visto una manera de hacer referencia solo con los punteros caso omiso en C++ que esto ya es menos complicado con la referencia, aun que la vdd es la misma borrega solo que con nombre distinto ), pero para ser sincero de alguna manera las referencias terminan a ser punteros.
Cada parametro en el que veas como prefijo "lp" quiere decir que se ESPERAN PUNTEROS. en este caso el api:
Declare Function ReadProcessMemory Lib "kernel32" (
ByVal hProcess As Long, <--- el prefijo "h" indica que se espera un HANDLE.
ByVal lpBaseAddress As Any, <--- el prefijo "lp" indica que se espera un puntero.
lpBuffer As Any, <--- el prefijo "lp" indica que se espera un puntero.
ByVal nSize As Long, <--- el prefijo "n" indica que se espera un entero ( Long(VB6) = int (C) e int(VB6) = short int(C) ).
lpNumberOfBytesWritten As Long <--- el prefijo "lp" indica que se espera un puntero.
) As Long
la api es igual a esta que C
BOOL WINAPI ReadProcessMemory(
__in HANDLE hProcess,
__in LPCVOID lpBaseAddress,
__out LPVOID lpBuffer,
__in SIZE_T nSize,
__out SIZE_T *lpNumberOfBytesRead
);
/*
__in <... Esto indica que es un parametro de solo entrada es decir que solo entra pero nada retorna por la misma
__out <... Esto indica que es un parametro de solo SALIDA o de RETORNO sobre el parametro pero que no le importa lo que tenga anteriormente.
__in y __out, Estos no se escriben aun que podrian representar de alguna manera:
__in = byval
__out = byref
**/
De hecho es mejor Declarar las apis a conforme a sus prototipos Predefenidos... es decir que la declaracion api deberia ser:
Declare Function ReadProcessMemory Lib "kernel32" (
ByVal hProcess As Long, _
ByVal lpBaseAddress As Long, _
ByVal lpBuffer As Long, _
ByVal nSize As Long, _
ByRef lpNumberOfBytesWritten As Long) As Long
pero como ya dije al final se pasaran lso punteros... es decir que lo correcto deberia de ser:
Declare Function ReadProcessMemory Lib "kernel32" (
ByVal hProcess As Long, _
ByVal lpBaseAddress As Long, _
ByVal lpBuffer As Long, _
ByVal nSize As Long, _
Byval lpNumberOfBytesWritten As Long) As Long
Estos prefijos ( "lp","sz","n","l", ... , "?" , ... ) se les conoce como declaracion hungara ( yo tengo la propia en C pero bueno no es dificil comprenderla en google encuentras un poco de informacion extra ).
Dulces Lunas!¡.
CitarByVal y Byref esta explicado de alguna manera ante los procesos y funciones personalisados (en la liga y todos han ido directo a este punto mas no al real problema de este hilo, las apis.), es decir, las que creamos o las de vb6 mas no a las APIS, asi que aqui te dejo una explicacion ante esto.:
aja ahi esta el punto, porque si el pasar ByVal a una api fuera nomas para "evitar que la funcion sobreescriba la variable pasada" pues en algunos casos donde iria ByVal supongo que cualquiera de las 2 formas seria valida no?, pues un caso:
suponiendo que quiero usar MessageBox
Declare Function MessageBox Lib "user32" Alias "MessageBoxA" (ByVal hwnd As Long, ByVal lpText As String, ByVal lpCaption As String, ByVal wType As Long) As Long
y en el parametro wType (icono a mostrar) NO me interesa si sobreescribe o no la variable asi que lo paso como ByRef:
Option Explicit
private Declare Function MessageBox Lib "user32" Alias "MessageBoxA" (ByVal hwnd As Long, ByVal lpText As String, ByVal lpCaption As String, ByRef wType As Long) As Long
Private Sub Command1_Click()
Dim Icono As Long
Icono = 64
Call MessageBox(Form1.hwnd, "Ejemplo", "xD", Icono)
MsgBox Icono 'muestra el valor a ver si sobreescribio la variable
End Sub
pues al ejecutar no sale el "MessageBox", y el msgbox muestra "64" , pues en este caso la API no sobreescribio la variable y tampoco mostro el mensaje, este tipo de cosas es que generan dudas, supongo que aqui tambien tienne que ver en si la API porque no sabemos como tratara o que hace con los datos o referencia que le pasamos.
ammm
http://msdn.microsoft.com/en-us/library/ms645505(v=vs.85).aspx
int WINAPI MessageBox(
__in_opt HWND hWnd,
__in_opt LPCTSTR lpText,
__in_opt LPCTSTR lpCaption,
__in UINT uType
);
En ningun lado veo que tenga un parametro de salida...deberias revisar la MSDN antes de hacer algo...
Dulces Lunas!¡.
ya lo entendi al 100% gracias, y tienes razon el uso del "As Any" es una mala practica, a veces confunde.