Cantidad variable de parámetros

User avatar
carlos vargas
Posts: 1421
Joined: Tue Oct 11, 2005 5:01 pm
Location: Nicaragua

Re: Cantidad variable de parámetros

Post by carlos vargas »

yo lo uso igual con instrucciones sql grandes, para mayor claridad, la leche seria si tuviera la funcionalidad que tiene en vfp, la cual es capaz de evaluar variables y poner en su lugar el valor.
por ejemplo

TEXT INTO cSql
SELECT CODIGO, NOMBRE, FECHA
FROM TABLA WHERE FECHA=<<DATE()>>
ENDTEXT

salu2
carlos vargas


Sends lines of text specified by TextLines to the current output device or memory variable. Visual FoxPro sends lines of text to the current output device until it encounters an ENDTEXT statement or until the program ends.

The current output device can include the main Visual FoxPro window, a user-defined window, a printer, a text file, or a low-level file.


TEXT [TO VarName [ADDITIVE] [TEXTMERGE] [NOSHOW] [FLAGS nValue] [PRETEXT eExpression]]
TextLines
ENDTEXT



Parameters
TextLines
Specifies text to send to the current output device. TextLines can consist of text, memory variables, array elements, expressions, functions, or any combination of these.

NoteNote
Visual FoxPro evaluates expressions, functions, memory variables, and array elements specified with TextLines only if you set SET TEXTMERGE to ON and enclose them with the delimiters specified by SET TEXTMERGE DELIMITERS. If SET TEXTMERGE is OFF, Visual FoxPro outputs expressions, functions, memory variables, and array elements as string literals along with their delimiters.


For example, Visual FoxPro evaluates and outputs the current date when you specify the DATE( ) function as TextLines only if SET TEXTMERGE is ON, and TextLines contains the function and the appropriate delimiters, such as <<DATE( )>>. If SET TEXTMERGE is OFF, Visual FoxPro outputs <<DATE( )>> as a string literal.

If you place comments within TEXT...ENDTEXT or after the single backslash character (\) or double backslash characters (\\), Visual FoxPro outputs the comments.

TO VarName
Specifies the memory variable name to use for passing the contents of the TEXT...ENDTEXT. This variable can already exist.

If the variable has not yet been declared, Visual FoxPro automatically creates it as a private variable. The TO clause operates regardless of how SET TEXTMERGE is set. If SET TEXTMERGE is set to a file, and the TO statement is included, Visual FoxPro outputs both the file and variable.

ADDITIVE
Determines whether the contents of the TO variable are overwritten or added to existing contents.

NoteNote
If the contents of TO VarName is not a string, Visual FoxPro always overwrites the contents in VarName.


TEXTMERGE
Enables evaluation of contents surrounded by delimiters without setting SET TEXTMERGE to ON.

NOSHOW
Disables display of the text merge to the screen.

FLAGS nValue
Specifies a numerical value that determines if output is suppressed to an output file, or if blank lines preceding any text are included in the output.

Value (additive) Description
1
Suppresses output to the file specified with the _TEXT System Variable.

2
When the NOSHOW clause is included, preserves blank lines preceding text that appears within TEXT...ENDTEXT. Setting nValue to 2 will separate current TEXT...ENDTEXT output from previous TEXT...ENDTEXT output with a line feed.

NoteNote
Combining an nValue setting of 2 and PRETEXT of 4 will separate current TEXT…ENDTEXT output from previous TEXT…ENDTEXT output with a line feed while removing empty lines in the TEXT...ENDTEXT output.




PRETEXT eExpression
Specifies a character string to insert before each line of the text merge contents between TEXT...ENDTEXT or a numeric expression.

The following table describes behaviors of the PRETEXT clause depending on the expression specified by eExpression.

eExpression PRETEXT behavior
Character expression
Insert the expression before each line of the text merge contents appearing between the TEXT...ENDTEXT statement. When using PRETEXT with TEXT...ENDTEXT, eExpression is limited to a maximum length of 255 characters.

eExpression overrides the contents of the _PRETEXT system variable. When eExpression contains an expression that needs to be evaluated, for example, a user-defined function (UDF), Visual FoxPro evaluates it only once when the TEXT command first appears.

Numeric expression
Specify additive flag values to determine behavior for the text merge contents appearing between the TEXT...ENDTEXT statement.

For example, a value of 7 specifies that Visual FoxPro eliminate all white space including spaces, tabs, and carriage returns. A value falling outside of the range of 0-15 produces an error.

NoteNote
Specifying a value of zero does not eliminate white space.


When eExpression is a numeric expression, you can use the _PRETEXT system variable to insert additional text after Visual FoxPro eliminates white space.


The following table lists numeric additive flags that you can use in eExpression to specify additional behavior.

Value (Additive) Description
1
Eliminate spaces before each line.

2
Eliminate tabs before each line.

4
Eliminate carriage returns, for example, blank lines, before each line.

8
Eliminate line feeds.

NoteNote
Unlike the _PRETEXT system variable, the PRETEXT clause does not have global scope and applies only to the TEXT...ENDTEXT statement in which it appears.


Characters removed using the PRETEXT clause apply only to text within the TEXT...ENDTEXT statement and not to evaluated text merged from cExpression. In the following example, the spaces in the memory variable, myvar, are not removed when merged with the text in TEXT...ENDTEXT:

CopyCode imageCopy Code
myvar = " AAA"
TEXT TO x NOSHOW ADDITIVE TEXTMERGE PRETEXT 7
Start Line
<<myvar>>
BBB
CCC
ENDTEXT


Collapse imageRemarks
By default, TEXT ... ENDTEXT sends output to the main Visual FoxPro window or the active window. To suppress output to the main Visual FoxPro window or the active window, issue SET CONSOLE OFF. To send output to a printer or a text file, use SET PRINTER. To send output from TEXT ... ENDTEXT to a low-level file that you created or opened using FCREATE( ) or FOPEN( ), store the file handle returned by FCREATE( ) or FOPEN( ) to the _TEXT system variable, which you can use to direct output to the corresponding low-level file.

NoteNote
The text merge process usually includes any white space that might appear before each line in a TEXT...ENDTEXT statement. However, the inclusion of white space might cause the text merge to fail, for example, when XML is used in a Web browser. You must remove such white space to avoid incorrectly formatted XML.


Nesting TEXT...ENDTEXT statements is not recommended, especially if using the PRETEXT clause because the nested statements can affect the format of the outer statements.

Collapse imageExample
Example 1

The following example demonstrates creating a low-level file called myNamesFile.txt and storing its file handle in the _TEXT system variable. The program exits if the myNamesFile.txt file cannot be created.

Visual FoxPro opens the customer table and outputs the names of the first ten contacts to myNamesFile.txt. Visual FoxPro outputs the text and results of the functions to the text file. The example uses MODIFY FILE to open myNamesFile.txt.

CopyCode imageCopy Code
CLEAR
CLOSE DATABASES
SET TALK OFF
SET TEXTMERGE ON
STORE FCREATE('myNamesFile.txt') TO _TEXT
IF _TEXT = -1
WAIT WINDOW 'Cannot create an output file. Press a key to exit.'
CANCEL
ENDIF
CLOSE DATABASES
OPEN DATABASE (HOME(2) + 'Data\testdata')
USE customer
TEXT
CONTACT NAMES
<<DATE( )>> <<TIME( )>>
ENDTEXT
WAIT WINDOW 'Press a key to generate the first ten names.'
SCAN NEXT 10
TEXT
<<contact>>
ENDTEXT
ENDSCAN
CLOSE ALL
MODIFY FILE myNamesFile.txt
ERASE myNamesFile.txt


Example 2

The following example shows a custom procedure that uses TEXT...ENDTEXT to store an XML DataSet to a variable. In the example, all spaces, tabs, and carriage returns are eliminated.

CopyCode imageCopy Code
PROCEDURE myProcedure
DO CASE
CASE nValue = 1
TEXT TO myVar NOSHOW TEXT PRETEXT 7
<?xml version="1.0" encoding="utf-8"?>
<DataSet xmlns="http://tempuri.org">
<<ALLTRIM(STRCONV(leRetVal.item(0).xml,9))>>
</DataSet>
ENDTEXT
OTHERWISE
ENDCASE
ENDPROC
Salu2
Carlos Vargas
Desde Managua, Nicaragua (CA)
Carlos Mora
Posts: 988
Joined: Thu Nov 24, 2005 3:01 pm
Location: Madrid, España

Re: Cantidad variable de parámetros

Post by Carlos Mora »

Tocayo,

todo esto de los pragmas vino justo a partir de eso: del reemplazo de variables por valores, muy parecido a lo que a ti te gustaría.
Mira la funcioncita 'Expand()' y luego el ejemplo de XML que subí, no es _exactamente_ lo que pides pero esta bastante cerca, es casi lo mismo. Es más: Puedes tener la sentencia SQL usando los parámetros $1, $2, etc.. y expandirlos en el momento que vayas a usarlo, usando variables. No repites toda la sentencia.

¿Funcionan los #pragmas con xHarbour?
Saludos
Carlos Mora
http://harbouradvisor.blogspot.com/
StackOverflow http://stackoverflow.com/users/549761/carlos-mora
“If you think education is expensive, try ignorance"
User avatar
lucasdebeltran
Posts: 1303
Joined: Tue Jul 21, 2009 8:12 am
Contact:

Re: Cantidad variable de parámetros

Post by lucasdebeltran »

Hola,

Añadiendo hbcompat.ch ya está disponible TEXT INTO cVariable

Un saludo
Muchas gracias. Many thanks.

Un saludo, Best regards,

Harbour 3.2.0dev, Borland C++ 5.82 y FWH 13.06 [producción]

Implementando MSVC 2010, FWH64 y ADO.

Abandonando uso xHarbour y SQLRDD.
User avatar
Antonio Linares
Site Admin
Posts: 37481
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain
Contact:

Re: Cantidad variable de parámetros

Post by Antonio Linares »

Carlos Vargas,

Yo tengo implementado este método (se puede usar como función) que hace la funcionalidad de FoxPro de sustituir variables :-)

Code: Select all

METHOD RunQuery( cSQLQuery, cTitle ) CLASS ...

   local oRs, nStart, nEnd, cVariable, cDlgTitle, uValue

   if ! Empty( cSQLQuery )
      while "[[" $ cSQLQuery
         uValue = Space( 100 )
         nStart = At( "[[", cSQLQuery )
         nEnd   = At( "]]", cSQLQuery )
         cVariable = SubStr( cSQLQuery, nStart + 2, nEnd - nStart - 2 )
         if "," $ cVariable
            cDlgTitle = SubStr( cVariable, At( ",", cVariable ) + 1 )
            cVariable = SubStr( cVariable, 1, At( ",", cVariable ) - 1 )
         endif
         if Empty( cDlgTitle )
            cDlgTitle = "Please write the value for " + cVariable
         endif
         MsgGet( cDlgTitle, "", @uValue )
         if "/" $ uValue
            uValue = StrTran( FW_ValToSQL( CToD( AllTrim( uValue ) ) ),;
                     "'", "" )
         else
            uValue = FW_ValToSQL( AllTrim( uValue ) )
         endif
         cDlgTitle = nil
         cSQLQuery = SubStr( cSQLQuery, 1, nStart - 1 ) + ;
                     uValue + ;
                     SubStr( cSQLQuery, nEnd + 2 )
      end

      // MsgInfo( cSQLQuery )
   endif
Las espressiones que quieres que se evaluen se escriben entre [[ ... ]]]
regards, saludos

Antonio Linares
www.fivetechsoft.com
Carlos Mora
Posts: 988
Joined: Thu Nov 24, 2005 3:01 pm
Location: Madrid, España

Re: Cantidad variable de parámetros

Post by Carlos Mora »

Estimadísimos,
Antonio Linares wrote: Dudo que Przemek pasará por alto algo asi. Tal vez haya otro uso para "..." que desconocemos.
Al menos encontré uno... otra grata sorpresa! Me expreso mejor con código, así es que aqui va el ejemplo de uso:

Code: Select all

#include 'Fivewin.ch'

FUNCTION Main()
   LOCAL bBlock:= {|...| Evalua( ... ) }
  
   MsgInfo( 'Sin este MsgInfo() no me muestra el otro, pero es irrelevante...' )

   Eval( bBlock, 'A', 'B', 'C' ) // =>Pops up 'Params :ABC'
   
   QUIT

FUNCTION Evalua( a, b, c )
RETURN MsgInfo( 'Params :' + a + b + c )
 
Estábamos buscando el significado de "..." como declaración, per su uso más significativo es en la llamada. Significa algo así como 'pasa como parámetros todos los parametros de la stack. Se me acaba de ocurrir... pasará también Self? Hay que probar.
Estas cosas las tengo que escribir en el blog, tengo que escribir en el blog, tengo que escribir en el blog....
Saludos
Carlos Mora
http://harbouradvisor.blogspot.com/
StackOverflow http://stackoverflow.com/users/549761/carlos-mora
“If you think education is expensive, try ignorance"
User avatar
Antonio Linares
Site Admin
Posts: 37481
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain
Contact:

Re: Cantidad variable de parámetros

Post by Antonio Linares »

Carlos,

Excelente ejemplo :-)

gracias!
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
cnavarro
Posts: 5792
Joined: Wed Feb 15, 2012 8:25 pm
Location: España

Re: Cantidad variable de parámetros

Post by cnavarro »

Carlos
++++1
C. Navarro
Hay dos tipos de personas: las que te hacen perder el tiempo y las que te hacen perder la noción del tiempo
Si alguien te dice que algo no se puede hacer, recuerda que esta hablando de sus limitaciones, no de las tuyas.
User avatar
Antonio Linares
Site Admin
Posts: 37481
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain
Contact:

Re: Cantidad variable de parámetros

Post by Antonio Linares »

Carlos,
Carlos Mora wrote:Solo se me ocurre una cuestion de orden y elegancia, una forma de hacer explícito el hecho de que vas a usar parámetros.
Tal vez el pcode generado podría llegar a mostrar alguna diferencia, no se...

Pero en lo personal lo he usado bastante, como en el ejemplo, y como podrás adivinar, con uso intensivo (es en las querys) y va fenomenal.

Y para añadir más cosas a la colección de cositas guapas, por si alguno todavía no lo conoce, van los siguientes #pragmas:

Code: Select all

#xcommand TEXT INTO <v> => #pragma __cstream|<v>:=%s
#xcommand TEXT INTO <v> ADDITIVE => #pragma __cstream|<v>+=%s
 
Esto nos permite escribir texto literal, que incluya incluso saltos de línea, como en:

Code: Select all

   TEXT INTO cTexto

      CREATE TABLE IF NOT EXISTS `validalta` (
        `id`         int(11) NOT NULL AUTO_INCREMENT,
        `fechanaci`  date,
        `nif`        varchar(9)  DEFAULT NULL,
        `mail`       varchar(50) DEFAULT NULL,
        `cuenta`     varchar(4) DEFAULT NULL,
        PRIMARY KEY (`id`),
        UNIQUE KEY `NIF` (`nif`)
      );
   ENDTEXT

   oServer:Command( cTexto )
 
o bien, XML combinado con la funcioncita de Expand

Code: Select all

               TEXT INTO cTransac
                  <tns:importAbsenceFiles xmlns:tns="http://echange.service.open.server.com">
                     <tns:absenceFilesToImport>
                        <tns:absenceFile>
                           <tns:absenceTypeAbbreviation>VACAC</tns:absenceTypeAbbreviation>
                           <tns:employeeIdentificationNumber>$1</tns:employeeIdentificationNumber>
                           <tns:startDate>$2</tns:startDate>
                           <tns:endDate>$3</tns:endDate>
                        </tns:absenceFile>
                     </tns:absenceFilesToImport>
                  </tns:importAbsenceFiles>
               ENDTEXT

               cTransac:= Expand( cTransac, oQuery:dni, oQuery:FechaInicio, oQuery:FechaFin )

 
Como te decía, entre SQL, XML y web... lo uso de forma intensiva, y ayuda a hacer la programación muchísimo más clara.
No encuentro la definición de ENDTEXT. Puedes comprobar en que se preprocesa ? gracias
regards, saludos

Antonio Linares
www.fivetechsoft.com
Carlos Mora
Posts: 988
Joined: Thu Nov 24, 2005 3:01 pm
Location: Madrid, España

Re: Cantidad variable de parámetros

Post by Carlos Mora »

Hola Antonio,

hasta donde entiendo, ENDTEXT marca el fin de la cadena, no se preprocesa. Funciona como la comilla final de una cadena cuando se abre con TEXT, marcando el final de la stream multilinea.
Existe desde un principio por el comando TEXT/ENDTEXT.

¿Has tenido algún inconveniente? Por acá va muy bien.

Un saludo
Saludos
Carlos Mora
http://harbouradvisor.blogspot.com/
StackOverflow http://stackoverflow.com/users/549761/carlos-mora
“If you think education is expensive, try ignorance"
User avatar
Antonio Linares
Site Admin
Posts: 37481
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain
Contact:

Re: Cantidad variable de parámetros

Post by Antonio Linares »

Carlos,

Tienes toda la razón.

Como TEXT INTO se preprocesa, pensé que ENDTEXT se preprocesaba tambien.

Funcionando correctamente, gracias :-)
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Antonio Linares
Site Admin
Posts: 37481
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain
Contact:

Re: Cantidad variable de parámetros

Post by Antonio Linares »

Carlos,

Cuando usas TEXT ... ENDTEXT, si no "pegas" el texto a la izquiera, este toma los espacios de la izquierda.

Como haces en tu código para que no tome esos espacios ?

Ejemplo:

Code: Select all

TEXT INTO cTest
   Uno
   Dos
   Tres
ENDTEXT

MsgInfo( cTest )
 
El texto "Uno" tiene 3 espacios a la izquierda. La cuestión es que entonces no puedes indentar el comando TEXT ... ENDTEXT o te incluye los espacios de la indentación en el texto. Has podido solucionar esto de alguna forma ? gracias
regards, saludos

Antonio Linares
www.fivetechsoft.com
Carlos Mora
Posts: 988
Joined: Thu Nov 24, 2005 3:01 pm
Location: Madrid, España

Re: Cantidad variable de parámetros

Post by Carlos Mora »

Hola Antonio,

no conozco una forma práctica de evitar el indentado. TEXT/ENDTEXT funcionan como si fueran comillas, no hace caso de nada excepto de lo que hay al final.
No le he dado mucha importancia hasta ahora porque lo he usado en situaciones donde esos espacios no me molestan, como sql o xml.

Y si, es cierto que a veces el código no queda tan bonito si tienes los bloques de texto fuera de la indentación natural dentro del código donde aparece. Lo veo un poco complicado, no hay nada de funcionalidad en el preprocesador para indentado porque, si lo piensas, el indentado es relevante al programador y no a como lo "lee" el compilador.

Si se me ocurre algo te lo digo.
Saludos
Carlos Mora
http://harbouradvisor.blogspot.com/
StackOverflow http://stackoverflow.com/users/549761/carlos-mora
“If you think education is expensive, try ignorance"
User avatar
Antonio Linares
Site Admin
Posts: 37481
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain
Contact:

Re: Cantidad variable de parámetros

Post by Antonio Linares »

Carlos,

ok, gracias.

Es una lástima porque perdemos la indentación del código PRG.
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
nageswaragunupudi
Posts: 8017
Joined: Sun Nov 19, 2006 5:22 am
Location: India
Contact:

Re: Cantidad variable de parámetros

Post by nageswaragunupudi »

yo lo uso igual con instrucciones sql grandes, para mayor claridad, la leche seria si tuviera la funcionalidad que tiene en vfp, la cual es capaz de evaluar variables y poner en su lugar el valor.
por ejemplo

TEXT INTO cSql
SELECT CODIGO, NOMBRE, FECHA
FROM TABLA WHERE FECHA=<<DATE()>>
ENDTEXT
FWH provides some help to enable writing SQL queries in a portable manner. I mean the same code will work for different RDMS, be it MySql, Access, MySql, Oracle, etc.

To start with, simple SELECT statement:

Code: Select all

   PRIVATE cDate := FW_ValToSQL( Date() )

   TEXT INTO cSql
   SELECT CODIGO, NOMBRE, FECHA
   FROM TABLA WHERE FECHA = &cDate
   ENDTEXT

   ? cSql
 
Result:

Code: Select all

   SELECT CODIGO, NOMBRE, FECHA
   FROM TABLA WHERE FECHA = '2015-03-14'
 
By default and if we established a connection to MySql server using FW_OpenAdoConnection(), the translation is for MySql.

The Query formatting has to be different for different RDBMS
If we earlier established connection to MsAccess database with FW_ * function and run the same code above the result is:

Code: Select all

   SELECT CODIGO, NOMBRE, FECHA
   FROM TABLA WHERE FECHA = #2015-03-14#
 
If we are connected to Oracle server and run the same code as above the result is:

Code: Select all

   SELECT CODIGO, NOMBRE, FECHA
   FROM TABLA WHERE FECHA = DATE '2015-03-14'
 
Now building INSERT and UPDATE queries, even using TEX INTO ..ENDTEXT is not that easy. We also need to keep our code portable. FWH provides very useful translates for this purpose. We need to include "adodef.ch" in our program. We include this anyway if we are using ADO.

Insert SQL:

Code: Select all

   cName    := "John"
   nAge     := 40
   dJoin    := STOD( "20001010" )
   lMarried := .f.
   cNote    := "David's brother"

   cSql  := SQL INSERT INTO EMPLOYEE ( NAME, AGE, JGDATE, MARRIED, NOTE ) ;
            VALUES ( cName, nAge, dJoin, lMarried, cNote )

   ? cSql

   cSql  := SQL UPDATE EMPLOYEE SET AGE = 30, JGDATE = STOD( "20071010" ), MARRIED = .T. ;
            WHERE ID = 201
   ? cSql

 
We can straight away use (x)Harbour variables here and there is no need to format them for SQL and also there is no need to remember which RDMS we are presently connected to.

Result for MySql:

Code: Select all

INSERT INTO EMPLOYEE ( `NAME`,`AGE`,`JGDATE`,`MARRIED`,`NOTE` ) VALUES ( 'John',40,'2000-10-10',0,'David''s brother' )
UPDATE EMPLOYEE SET `AGE` = 30,`JGDATE` = '2007-10-10',`MARRIED` = 1 WHERE ID = 201
 
If we connect to MsAccess and run the same code the result is:

Code: Select all

INSERT INTO EMPLOYEE ( [NAME],[AGE],[JGDATE],[MARRIED],[NOTE] ) VALUES ( 'John',40,#2000-10-10#,0,'David''s brother' )
UPDATE EMPLOYEE SET [AGE] = 30,[JGDATE] = #2007-10-10#,[MARRIED] = 1 WHERE ID = 201
 
FWH now provides safe portability of code for Access, MySql, MSSql, SqLite3 and Oracle.

I advise using facilities provided by FWH and save lots of time in formatting SQL statements as well as lot of time in debugging your sql statements.
Regards

G. N. Rao.
Hyderabad, India
antolin
Posts: 475
Joined: Thu May 10, 2007 8:30 pm
Location: Sevilla

Re: Cantidad variable de parámetros

Post by antolin »

Muchas gracias.

La verdad, es que TEXT ... END TEXT ya existía en Clipper Summer 87, pero no me acordaba, además sólo iba con SCREEN y PRINTER, creo, ni mi imaginaba que funcionaría también aquí. Qué maravilla.
Peaaaaaso de foro...
Post Reply