FoxPro/Visual FoxPro - Llamar variables de un Procedure

 
Vista:

Llamar variables de un Procedure

Publicado por Raúl (8 intervenciones) el 01/02/2017 17:16:10
Tengo problemas al llamar los parametros de mi PROCEDURE, básicamente mi problematica se resume a esto y el ejemplo presentado ilustra de una manera simple esta situación, así que favor de evitar comentarios sobre como sumar 3 numeros y enfocarse al comando PROCEDURE. Este es el código:

PROCEDURE sumatoria(nNumeric1, nNumeric2, nNumeric3)
RETURN (&nNumeric1 + &nNumeric2 + &nNumeric3)
ENDPROC

Cuando lo corro me marca: Missing Operand (en este caso), pero lo he intentado de varias formas y me parece que el error es sobre como llamo mis parametros

Saludos,
Valora esta pregunta
Me gusta: Está pregunta es útil y esta claraNo me gusta: Está pregunta no esta clara o no es útil
0
Responder
Imágen de perfil de Mauricio Antonio
Val: 471
Plata
Ha mantenido su posición en FoxPro/Visual FoxPro (en relación al último mes)
Gráfica de FoxPro/Visual FoxPro

Llamar variables de un Procedure

Publicado por Mauricio Antonio (1541 intervenciones) el 01/02/2017 19:51:10
Prueba esto y por favor no preguntes nada:
LOCAL nnum1, nnum2, nnum3, suma
nnum1 = 15
nnum2 = 75
nnum3 = 100
suma = 0
*
DO sumatoria WITH nnum1, nnum2, nnum3, suma
? suma
*
PROCEDURE sumatoria
LPARAMETERS nNum1, nNum2, nNum3, suma
*
suma = nnum1 + nnum2 + nnum3
RETURN suma
ENDPROC
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

Llamar variables de un Procedure

Publicado por Raúl (8 intervenciones) el 01/02/2017 20:12:27
No va a ser una pregunta, más bien un comentario: Manda error tu propuesta
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar
Imágen de perfil de Mauricio Antonio
Val: 471
Plata
Ha mantenido su posición en FoxPro/Visual FoxPro (en relación al último mes)
Gráfica de FoxPro/Visual FoxPro

Llamar variables de un Procedure

Publicado por Mauricio Antonio (1541 intervenciones) el 01/02/2017 21:22:39
puedes describir el error? hasta el viernes viene el adivino.......
No lo puedes corregir?
Antes de postearlo lo probe y funciona bien.....
lo acabo de ejecutar y funciona sin errores.
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

Llamar variables de un Procedure

Publicado por Raúl (8 intervenciones) el 01/02/2017 23:15:36
jajaja igual y con el adivino tienes más suerte. Ya me ayudaron en el comentario de abajo, gracias por ........ intentar, creo

Saludos,
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar
sin imagen de perfil
Val: 1.011
Oro
Ha mantenido su posición en FoxPro/Visual FoxPro (en relación al último mes)
Gráfica de FoxPro/Visual FoxPro

Llamar variables de un Procedure

Publicado por Fidel José (657 intervenciones) el 01/02/2017 22:24:58
Sintetizando: el problema es esa macrosustitucion que intentas en la función.

PROCEDURE sumatoria(nNumeric1, nNumeric2, nNumeric3)
RETURN (nNumeric1 + nNumeric2 + nNumeric3)
ENDPROC

Lo que se recomienda es controlar, por lo menos, dos cosas:
1) Si se pasaron todos los parámetros
2) Si los parámetros tienen el tipo de valor requerido
En procedimientos más complejos, puede que se necesite comprobar si un parámetro está dentro de un rango.

Tienes que tener en cuenta que, en Visual Fox, el parámetro que se omite asume el valor .F.

Por otra parte, recomiendo (por más clara) la escritura de la siguiente forma:
1
2
3
4
5
6
7
8
PROCEDURE Sumatoria
LPARAMETERS tnNumeric1, tnNumeric2 , tnNumeric3
LOCAL lnSuma
lnSuma = IIF(VARTYPE(m.tnNumeric1)="N",m.tnNumeric1,0 ) ;
		+ IIF(VARTYPE(m.tnNumeric2)="N",m.tnNumeric2,0 ) ;
		+ IIF(VARTYPE(m.tnNumeric3)="N",m.tnNumeric3,0 )
RETURN m.lnSuma
ENDPROC
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

Llamar variables de un Procedure

Publicado por Raúl (8 intervenciones) el 01/02/2017 23:13:51
Si, en efecto es la macrosustitución que intentaba, cuando hago macrosustituciones con string si funciona, pero ahora que la use con númerico ya no me dejo. Veo que le pones una m. al inicio del parametro que llamas, ¿siempre debe ser así?

Y gracias, esto que pones si me funciono.
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar
sin imagen de perfil
Val: 1.011
Oro
Ha mantenido su posición en FoxPro/Visual FoxPro (en relación al último mes)
Gráfica de FoxPro/Visual FoxPro

Llamar variables de un Procedure

Publicado por Fidel José (657 intervenciones) el 01/02/2017 23:32:08
Los prefijos m. se utilizan para indicarle a visual Fox que se trata de una variable de memoria.
Recuerda que si un campo del cursor en el área de trabajo tiene el mismo nombre que una variable de memoria, el campo del cursor tiene privilegio, salvo que no corresponda.
Create cursor prueba ("campo1" n(12,2) )
Campo1 = 0 && esto solamente puede igualar a cero una variable de memoria, en este caso PRIVATE, porque no se declaró antes.

Pero:
Campo1 = 20

INSERT INTO PRUEBA (campo1) values ( 40 )

lnResult = Campo1 + 100 && resultado será 140, PORQUE TOMA EL VALOR DE Prueba.Campo1

Pero
lnREsult = m.campo1 + 100
? lnResult && el resultado será 120, porque m.campo1 es la variable de memoria.

Escribir el prefijo cuando corresponda, no solo ayuda a entender un código escrito hace algún tiempo, sino que le ahorra tiempo a Visual Fox al no tener que verificar, antes de tomar el valor, si existe un cursor en el área de trabajo y si este cursor tiene un campo que se llama igual que la variable. En procesos que tienen miles de iteraciones, se vuelve realmente más rápido.

Y cuándo se debe escribir el prefijo m. ?
LOCAL lnVariable && no se admite el prefijo porque solamente se puede definir una variable de memoria mediante LOCAL
lnVariable = 0 && no se necesita el prefijo, porque esta sintaxis corresponde solamente a una variable de memoria

lnVariable = m.lnVariable + 1 && aquí es donde se necesita el prefijo m.
IF m.lnVariable > 1000
MiProcedure(m.lnVariable)
ENDIF
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

Llamar variables de un Procedure

Publicado por Raúl (8 intervenciones) el 01/02/2017 23:37:30
Gracias, tendre en cuenta las preferencias de nombres iguales, realmente fuiste de gran ayuda.
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar
sin imagen de perfil
Val: 1.011
Oro
Ha mantenido su posición en FoxPro/Visual FoxPro (en relación al último mes)
Gráfica de FoxPro/Visual FoxPro

Llamar variables de un Procedure

Publicado por Fidel José (657 intervenciones) el 02/02/2017 00:08:31
Las macrosustituciones deben ser evitadas porque son muy lerdas, siempre que sea posible.

Ejemplo:
lcString = "1236.41"
? VAL(m.lcstring) && función específica
lnNumeric = VAL(m.lcstring)
? VARTYPE(lnNumeric) && "N"
lnNUmeric = EVALUATE(m.lcstring)
? VARTYPE(lnNumeric) && "N"
? lnNUmeric

Evaluate() es una función muy poderosa, aunque debe utilizarse allí donde corresponda.
Fijate en este ejemplo:
LOCAL a,b,h
a = 30
b = 0.35
h = 120
lcString_Form = "a * b + h"
lnResult = EVALUATE(m.lcstring_form)
? lnREsult

Entonces puede que tenga la fórmula de lcSTring_form en una tabla, y que en el proceso, previamente le asigne valor a las variables y con EVALUATE() se determina el valor. Este método es utilizado en escenarios donde el cálculo puede variar de acuerdo a términos comerciales, disposiciones legales o convencionales, etc. (Ejemplo, cálculo de sueldos, cálculo de tarifas de transporte, etc.)

También con EVALUATE se puede revelar el valor de un cursor cuyo nombre se desconoce, o de un campo cuyo nombre puede variar.
lcCursor = "CursorEnUso"
lcCampo = "MiCampo"

lxValor = EVALUATE(m.lcCursor + "." + m.lcCampo)

Para el caso, como conocemos el nombre, podría ser
lxValor = EVALUATE(m.lcCursor + ".MiCampo")

Y por qué ignoramos el nombre de un cursor?. Bueno, en un procedure que determina algún cálculo, el nombre del cursor puede venir como parámetro para independizarse del origen de datos.

lcNombreCliente = Ret_NombreCliente(Alias() , 3 )

PROCEDURE Ret_NombreCliente
LPARAMETERS tcCursor , tnField
* Ejemplo
* tcCursor = "CLIENTES"
* tnField = 3
RETURN EVALUATE(m.lccursor + "."+FIELD(m.lnfield,m.lccursor))

En cambio, la macrosustitución se debe utilizar en un caso como este
loREsp._Items = m.lnItems

lcString = LEFT(m.lcString,LEN(m.lcString)-1)
TEXT TO lcSelect TEXTMERGE NOSHOW PRETEXT 15
SELECT <<lcString>> FROM <<tcCursor>> WHERE <<tcIncluye>> INTO ARRAY laSum
ENDTEXT

&lcSelect
lnTally = _tally

A muchos le parece más elengante la función EXECSCRIPT(), pero tiene la penalización del tiempo: Esta poderosa función escribe un archivo prg y crea la versión objeto (fxp) que es la que entiende Visual Fox. Por eso en este caso será más rápida la macrosustitución.

EXECSCRIPT() debe reservarse para el caso en que se necesiten ejecutar varias líneas de código, separadas por CHR(13), cuando este código deba generarse dentro del programa, o pueda ser generado por un usuario experto en alguna tabla. Puede recibir parámetros y devolver un valor, cosa que no puede esperarse de la macrosustitución.

Acá va una muestra sencilla de lo que puede hacer Execscript()
1
2
3
4
5
6
7
8
9
10
11
12
13
LOCAL lnResulta
lcString = ""
lcString = m.lcString ;
	+ [LPARAMETERS ta,tb,th ]+CHR(13);
	+ [ta = EVL(m.ta,0) ] + CHR(13);
	+ [tb = EVL(m.tb,0) ] + CHR(13);
	+ [th = EVL(m.th,0) ] + CHR(13);
	+ [LOCAL lnResult] + CHR(13);
	+ [lnResult = m.ta * m.tb + m.th]+CHR(13) ;
	+ [RETURN m.lnResult]+CHR(13)
 
lnResulta = EXECSCRIPT(m.lcString,10,0.850,200)
MESSAGEBOX(m.lnResulta)
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar