FiveTech Support Forums

FiveWin / Harbour / xBase community
Board index FiveWin para Harbour/xHarbour Usar o no variables publicas.
Posts: 607
Joined: Mon Mar 04, 2013 04:32 PM
Usar o no variables publicas.
Posted: Tue Apr 28, 2020 01:21 PM
Hola el tema es este

Variables publicas si o no. ?
yo siempre he leido que no es aconsejable utilizarlas, por eso ahora utilizo el siguiente sistema.
como siempre tenemos que acceder a variables que estan en otros modulos. Yo declaro las variables static.
y las paso a otros modulos asi.

Code (fw): Select all Collapse
FUNCTION GetWndMain()
RETURN oWndMain

y en el modulo que la tengo que utilizar.
Code (fw): Select all Collapse
oWndMain := GetWndMain()


El tema funciona bien, pero en cada modulo que voy a utilizarla, que sera en casi todos tengo que llamar a la funcion.
Si utilizara variable publica me ahorraria esto, seria mejor?

¿Como lo haceis vosotros para acceder a una variable de otro modulo?

Espero haberme explicado bien, muchas gracias por vuestra ayuda.

Saludos.

Jose.
Fwh 24.07 64 bits + Harbour 64 bits 3.2dev(r2407221137) + MSVC64
Posts: 8515
Joined: Tue Dec 20, 2005 07:36 PM
Re: Usar o no variables publicas.
Posted: Tue Apr 28, 2020 02:00 PM

Puedes usarlo sin ningún problema. cuando salga del programa use CLEAR MEMORY.

João Santos - São Paulo - Brasil - Phone: +55(11)95150-7341
Posts: 6755
Joined: Wed Feb 15, 2012 08:25 PM
Re: Usar o no variables publicas.
Posted: Tue Apr 28, 2020 02:03 PM

Como dice el compañero, se pueden seguir utilizando, pero a mí particularmente no me gusta su uso, prefiero sólo utilizar las variables definidas en su propio módulo, por lo que en todo caso utilizo la técnica que has descrito ( llamar a la function que me devuelva la variable que utilizo )

Cristobal Navarro

Hay dos tipos de personas: las que te hacen perder el tiempo y las que te hacen perder la noción del tiempo

El secreto de la felicidad no está en hacer lo que te gusta, sino en que te guste lo que haces
Posts: 174
Joined: Sat Feb 23, 2013 10:04 AM
Re: Usar o no variables publicas.
Posted: Tue Apr 28, 2020 02:56 PM

Yo tampoco utilizo ni Public ni Private, pero si tengo una Public oApp

Posts: 6755
Joined: Wed Feb 15, 2012 08:25 PM
Re: Usar o no variables publicas.
Posted: Tue Apr 28, 2020 03:11 PM
Antonio Mart. wrote:Yo tampoco utilizo ni Public ni Private, pero si tengo una Public oApp

Sí, también es una práctica muy habitual, en la que existe una clase TApp o algo asi
En ese caso, lo lógico es convertir a DATAs cada una de esas variables públicas y obtenerlas a partir del objeto oApp, o, yo incluso veo mejor hacer en una DATA un hash que contenga las el valor de las antiguas variables públicas y, en el caso de ser static la variable oApp, y no public devolver el hash del key que envías como parámetro.
Utilizando este método, sólo necesitas una llamada a una sola function
Code (fw): Select all Collapse
Function GetVarPublic( cVar )
// Comprobar que lo que recibe como parámetro está definido como key en el hash ( hb_HHashkey() )
Return oApp:aPublics[ cVar ]
Cristobal Navarro

Hay dos tipos de personas: las que te hacen perder el tiempo y las que te hacen perder la noción del tiempo

El secreto de la felicidad no está en hacer lo que te gusta, sino en que te guste lo que haces
Posts: 817
Joined: Sun Jun 15, 2008 07:47 PM
Re: Usar o no variables publicas.
Posted: Tue Apr 28, 2020 09:48 PM
Creo que deberías usar lo que más te guste o más práctico sea para ti.

En nuestro querido y viejo clipper había unos límites fáciles de alcanzar de variables públics y privates en la TABLA DE SÍMBOLOS, pero esa limitación ya no existe en Harbour.
Personalmente por inercia tampoco las utilizo, pero me reitero sólo por inercia.

Yo como soy muy de POO uso una clase TCore o TKernel compuesta solo de datas que serían las variables que voy a usar en mis prg
Es más se me ocurre que si esas datas son CLASDATA no habría ni que instaciar un objeto de esa clase y se podría hacer algo así:
Code (fw): Select all Collapse
CLASS TKernel
    CLASSDATA xVar1
    CLASSDATA xVar2
    CLASSDATA xVar3
ENDCLASS
// Y en el programa se podría hacer
TKernel:xVar1 := "Esto es una prueba"
? TKernel:xVar1


Es mas podría haber una sola CLASSDATA de tipo Hash que aumentaria segú se requiera:
Code (fw): Select all Collapse
CLASS TKernel
    CLASSDATA hVar 
ENDCLASS

TKernel:hVar[ "DNI" ] := "89436870T"
? TKernel:hVar[ "DNI" ]


Bueno lo dejo porque se me está disparando la perola!!!
:-)
______________________________________________________________________________

Sevilla - Andalucía
Posts: 1789
Joined: Tue Oct 11, 2005 05:01 PM
Re: Usar o no variables publicas.
Posted: Tue Apr 28, 2020 09:52 PM
Últimamente me hecho adicto a los hash
en mis app tengo un
Code (fw): Select all Collapse
en el modulo inicial
PUBLIC hGlobal := {=>}
hGlobal[ "userid" ] :=
hGlobal[ "userlevel" ] :=
hGlobal[ "usermodules" ] :=

y asi, las que necesite.
Salu2

Carlos Vargas

Desde Managua, Nicaragua (CA)
Posts: 1364
Joined: Wed Jun 21, 2006 12:39 AM
Re: Usar o no variables publicas.
Posted: Tue Apr 28, 2020 10:54 PM
Hay una clase que yo utilizo que se llama TPublic, donde defines solo una variable pública y declaras las que quieras dentro de ella.

Code (fw): Select all Collapse
Public o

With Object o := TPublic() : New()
    :Add( "usuario" )
    :Add( "passw" )
EndWith


Tiene varios métodos para gestionarla.
Saludos
Posts: 44158
Joined: Thu Oct 06, 2005 05:47 PM
Re: Usar o no variables publicas.
Posted: Wed Apr 29, 2020 01:16 AM

Horacio,

Puedes publicar aqui el código fuente de la clase TPublic que comentas ? gracias

regards, saludos

Antonio Linares
www.fivetechsoft.com
Posts: 1364
Joined: Wed Jun 21, 2006 12:39 AM
Re: Usar o no variables publicas.
Posted: Wed Apr 29, 2020 02:06 AM
La clase es de Daniel Andrade, un coterraneo :-)


Code (fw): Select all Collapse
 *  -----------------------------------------------------------------------------
 *  TPublic()
 *  Clase para el reemplazo de Variables Publicas
 *  Version 2.2b - 01/04/2003
 *
 *  Andrade A. Daniel
 *  Rosario - Santa Fe - Argentina
 *
 *  andrade_2knews@hotmail.com
 *  http://www.dbwide.com.ar
 *
 *  Aportes: [ER]   Eduardo Rizzolo
 *           [WA]   Wilson Alves - <!-- e --><a href="mailto:wolverine@sercomtel.com.br">wolverine@sercomtel.com.br</a><!-- e --> 18/05/2002
 *           [JJMG] Juan J. Mendez Gonzalez
 *
 *  DATAS
 *  -----------------------------------------------------------------------------
 * aVars      - Arreglo de variables
 * cName      - Nombre ultima variable accedida
 * nPos       - Valor ultimo variable accedida
 * lAutomatic - Asignación automatica, por defecto TRUE [WA]
 *
 *  METODOS
 *  -----------------------------------------------------------------------------
 * New()      - Contructor
 * Add()      - Agrega/define nueva variable
 * Del()      - Borra variable
 * Get()      - Accede a una veriable directamente
 * Set()      - Define nuevo valor directamente
 * GetPos()   - Obtener la posición en el array
 * Release()  - Borra todas las variables
 * IsDef()    - Chequea si una variable fue definida
 * Clone()    - Clona la DATA aVars
 * nCount()   - Devuelve cantidad de variables definidas
 * Save()     - Salva DATA aVars
 * Restore()  - Restaura DATA aVars
 *
 *  NOTA
 *  -----------------------------------------------------------------------------
 * Para acceder al valor de una variable, se puede hacer de 2 formas,
 * una directa usando oPub:Get("Codigo") o por Prueba/Error oPub:Codigo,
 * este último es mas simple de usar pero más lento.
 *
 * Para definir un nuevo valor a una variable tambien puede ser por 2 formas,
 * directamente por oPub:Set("Codigo", "ABC" ), o por Prueba/Error
 * oPub:Codigo := "ABC".
 *
 * Atencion: Los metodos Get() y Set() no controlan si la variable existe,
 * para ganar en velocidad.
 *
 * Las variables definidas NO son case sensitive.
 *
 *  MODIFICACIONES Y AGREGADOS
 *  -----------------------------------------------------------------------------
 * 2.2b Correción Bug en metodo Add() sobre FWH.
 * 2.2a Modificado para não restringir o número de variáveis em [x]Harbour [WA]
 * 2.2  Modificada para funcionar en [x]Harbour
 *
 * 2.1  Se guarda el Nombre y Posición de la última variable accedida para incrementar
 *      la velocidad. (Implementado por Eduardo Rizzolo)
 *
 *  EJEMPLO
 *  -----------------------------------------------------------------------------
 * FUNCTION Test()
 * local oP := TPublic():New(), aSave, nPos
 *
 * oP:Add("Codigo")           // Defino variable sin valor inicial
 * oP:Add("Precio", 1.15)     // Defino variable con valor inicial
 * oP:Add("Cantidad", 10 )
 * oP:Add("TOTAL" )
 *
 * // Acceso a variables por prueba/error
 * oP:Total := oP:Precio * oP:Cantidad
 *
 * // Definicion y Acceso a variables directamente
 * oP:Set("Total", oP:Get("precio") * oP:Get("CANTIDAD") )
 *
 * oP:Del("Total")         // Borro una variable
 * ? oP:IsDef("TOTAL")     // Varifico si existe una variable
 *
 * nPos := oP:GetPos("Total") // Obtengo la posición en el array
 * oP:aVars[nPos,2] := 0      // Modifico el Valor en el array directo
 *
 * aSave := oP:Save()      // Guardo las Variables
 * oP:Release()         // Borro TODAS las variables
 * oP:Restore( aSave )     // Restauro las variables
 *
 * oP:End()       // Termino
 *
 * RETURN NIL
 *
 *  EXEMPLO (Asignación Automática)
 *
 * FUNCTION MAIN()
 * LOCAL oP:=TPublic():New(.T.)
 *
 * op:nome     := "Wilson Alves"
 * op:Endereco := "Rua dos Cravos,75"
 * op:Cidade   := "Londrina-PR"
 * op:Celular  := "9112-5495"
 * op:Empresa  := "WCW Software"
 *
 * ? op:Nome,op:Endereco,op:Cidade,op:celular,op:empresa
 *
 * op:End()
 * RETURN NIL
 *
 *

# include "FiveWin.ch"

#ifdef __HARBOUR__
  # xtranslate BYNAME <V> [, <VN> ]     => ::<V> := <V> [; ::<VN> := <VN> ]
  # xtranslate BYNAME <V> DEFAULT <Val> => ::<V> := BYDEFAULT <V>, <Val>
  # xtranslate BYNAME <V> IFNONIL       => if <V> != NIL ; ::<V> := <V> ; endif
  # xtranslate BYDEFAULT <V>, <Val>     => if( <V> == NIL, <Val>, <V> )
#endif

*
* TPublic()
*
CLASS TPublic

   DATA  lAutomatic  AS LOGICAL     INIT .T.    // [WA]

   DATA  aVars       AS ARRAY       INIT NIL
   DATA  nPos        AS NUMERIC     INIT 0   READONLY // [ER]
   DATA  cName       AS CHARACTER   INIT ""  READONLY // [ER]

   METHOD New( lAutomatic )
   METHOD End()      INLINE ::Release()

   METHOD Add( cName, xValue )
   METHOD Del( cName )
   METHOD Get( cName )
   METHOD Set( cName, xValue )

   METHOD GetPos( cName )

   METHOD Release()
   METHOD IsDef( cName )

   METHOD Clone()    INLINE aClone( ::aClone )
   METHOD nCount()      INLINE Len( ::aVars )

   METHOD Save()     INLINE aClone( ::aVars )
   METHOD Restore( aVars ) INLINE ::aVars := aClone( aVars )

#ifdef __HARBOUR__
   ERROR HANDLER OnError( uParam1 )
#else
   ERROR HANDLER OnError( cMsg, nError )
#endif

ENDCLASS

*
*  TPublic:New()
*
METHOD New( lAutomatic ) CLASS TPublic // [WA]

   ::aVars := {}

   BYNAME  lAutomatic DEFAULT .T.   // [WA]

RETURN Self

*
*  TPublic:Add()
*
METHOD Add( cName, xValue ) CLASS TPublic // [ER]

  if cName != NIL
    if (::nPos := aScan( ::aVars, { |e,n| e[1] == AllTrim(Upper(cName)) } )) != 0
      ::aVars[::nPos,2] := xValue

#ifndef __HARBOUR__                 // [WA]
    elseif Len(::aVars) < 4000      // [JJMG]
      aAdd( ::aVars, { AllTrim(Upper(cName)), xValue } )
      ::nPos := Len(::aVars)

    else
      MsgAlert("Demasiadas variables definidas para la Clase TPublic()")

#else
    else
      aAdd( ::aVars, { AllTrim(Upper(cName)), xValue } )
      ::nPos := Len(::aVars)
#endif                              // [WA]

    endif

    ::cName  := cName
  endif

RETURN Self

*
*  TPublic:Del()
*
METHOD Del( cName ) CLASS TPublic
   local nPos

   if cName != NIL
      if (nPos := aScan( ::aVars, { |e,n| e[1] == AllTrim(Upper(cName)) } )) != 0
         aDel( ::aVars, nPos )
         ::aVars := aSize( ::aVars, Len(::aVars) - 1 )

         ::nPos   := 0
         ::cName  := ""
      endif
   endif

RETURN Self

*
*  TPublic:Get()
*
METHOD Get( cName ) CLASS TPublic                  // [by ER]

   if cName != ::cName
      ::nPos   := aScan( ::aVars, { |e,n| e[1] == AllTrim(Upper(cName)) } )
      ::cName  := cName
   endif

RETURN ::aVars[::nPos,2]

*
*  TPublic:Set()
*
METHOD Set( cName, xValue ) CLASS TPublic             // [by ER]

   if cName != ::cName
      ::nPos   := aScan( ::aVars, { |e,n| e[1] == AllTrim(Upper(cName)) } )
      ::cName  := cName
   endif

   ::aVars[::nPos,2] := xValue

RETURN Self

*
*  TPublic:GetPos()                         // [by ER]
*
METHOD GetPos( cName ) CLASS TPublic

   ::cName  := cName

RETURN ::nPos := aScan( ::aVars, { |e,n| e[1] == AllTrim(Upper(cName)) } )


*
*  TPublic:Release()
*
METHOD Release() CLASS TPublic

   ASIZE(::aVars,0)
   ::cName  := ""
   ::nPos   := 0

RETURN Self

*
*  TPublic:IsDef()
*
METHOD IsDef( cName ) CLASS TPublic                // [by ER]

   local lOk := .F.

   if cName != NIL
      if (::nPos := aScan( ::aVars, { |e,n| e[1] == AllTrim(Upper(cName)) } )) != 0
         ::cName := cName
         lOk := .T.
      endif
   endif

RETURN lOk

*
*  OnError()
*
#ifdef __HARBOUR__
   METHOD OnError( uParam1 ) CLASS TPublic
      local cMsg   := __GetMessage()
      local nError := If( SubStr( cMsg, 1, 1 ) == "_", 1005, 1004 )
#else
   METHOD OnError( cMsg, nError ) CLASS TPublic
      local uParam1 := GetParam( 1, 1 )
#endif

   cMsg := Upper( AllTrim( cMsg ))

   if SubStr( cMsg, 1, 1 ) == "_"
      cMsg := SubStr( cMsg, 2 )

      if cMsg == Upper(::cName)
         ::aVars[::nPos,2] := uParam1

      elseif ( ::nPos := aScan( ::aVars, { |e,n| e[1] == cMsg } ) ) != 0
         ::cName  := cMsg
         ::aVars[::nPos,2] := uParam1

      else

         if !::lAutomatic  // [WA]
            _ClsSetError( _GenError( nError, ::ClassName(), cMsg ) )
            ::cName  := ""
            ::nPos   := 0
         else
            ::add(cmsg)
            ::aVars[::nPos,2] := uParam1
         endif
      endif
   else
      if cMsg == Upper(::cName)           // [by ER]
         RETURN ::aVars[::nPos,2]

      elseif ( ::nPos := aScan( ::aVars, { |e,n| e[1] == cMsg } ) ) != 0
         ::cName  := cMsg
         RETURN ::aVars[::nPos,2]
      else
         _ClsSetError( _GenError( nError, ::ClassName(), cMsg ) )
         ::cName  := ""
         ::nPos   := 0
      endif
   endif

RETURN NIL

// Andrade Daniel (2001-2003)


Saludos
Posts: 652
Joined: Wed Oct 19, 2005 12:03 PM
Re: Usar o no variables publicas.
Posted: Thu Apr 30, 2020 09:27 AM
Bueno hace años que lo que utilizo esto, que realmente lo saque de algun colaborador de nuestro foro, y disculpas por no recordar de quien, pero me funciona perfecto
En el progama principal
Code (fw): Select all Collapse
# include "fivewin.ch"


 memvar oApp

function main()
 
 variables locales 
 oApp := TApplication()


      oApp:habilito:=GetpvProfString("dgi","habilito",,cinit)
      oApp:dirpdf := GetpvProfString("camino","dirpdf",,cinit)
      oApp:dirdoc := GetpvProfString("camino","dirdoc",,cinit)
      oApp:curproga := GetpvProfString("camino","curproga",,cinit)
      oApp:dirfac := GetpvProfString("camino","dirfac",,cinit)
      oApp:             etc , etc

  if pasaje("variable")
      database oVar
      dbgotop()
      oApp:fecha := oVar:fechamae
      oApp:ndola := oVar:dolar
      oApp:ndola30 := oVar:dolar30
      etc, etc 
 
  endif

 

return nil


////////////////////////////////////////////////////////////////////////////////////////////////
CLASS TApplication

   DATA dirpdf INIT Space(120)
   DATA dirdoc INIT Space(120)
   DATA docvarios INIT Space(120)
   DATA usuario INIT (GetpvProfString("usuario","nombre",,(GetWinDir()+"\mega.ini")))
   DATA permiso INIT (GetpvProfString("lugares","ctasctes",,(GetWinDir()+"\mega.ini")))
   DATA permiso1 INIT ( GetpvProfString("lugares","alicuota",,(GetWinDir()+"\mega.ini")))
   DATA contador INIT (GetpvProfString("camino","contpath",,(GetWinDir()+"\mega.ini")))
   DATA privado INIT (GetpvProfString("lugares","privado",,(GetWinDir()+"\mega.ini")))
   DATA destinozip INIT (GetpvProfString("camino","zip",,(GetWinDir()+"\mega.ini")))
   DATA desOcompra INIT (GetpvProfString("camino","ocompra",,(GetWinDir()+"\mega.ini")))
   DATA correo INIT ""
   DATA puerto INIT 0
   DATA smtp INIT ""
   DATA blat INIT ""
   DATA imppdf INIT ""
   DATA imppre INIT ""
   // etc y mas etc

ENDCLASS


return nil


Y después en cualquier módulo que utilizo lo que hago es

Code (fw): Select all Collapse
memvar oApp

function pepito()
 bla bla bla

            IF  ShellExecute( , "open",   ( oApp:dirfac + oCae:nombre + ".pdf" ),,, 1 ) != 2
               cldata( aObj )
               RETURN NIL
            ENDIF


Funciona bien.


Luis
Posts: 1956
Joined: Fri Oct 07, 2005 07:08 PM
Re: Usar o no variables publicas.
Posted: Thu Mar 25, 2021 12:33 PM
Code (fw): Select all Collapse
en el modulo inicial
PUBLIC hGlobal := {=>}
hGlobal[ "userid" ] :=
hGlobal[ "userlevel" ] :=
hGlobal[ "usermodules" ] :=


esto me da error al compilar con harbour
Code (fw): Select all Collapse
#include "fivewin.ch"

public hGlobal:= {=>}

FUNCTION main()
   hGlobal["uno"]:= "valor agregado"

   ? hGlobal["uno"]
   

   RETURN NIL


Source\clases\main.prg(15) Error E0001 Statement not allowed outside of procedure or function
FWH 21.02
Harbour 3.2.0dev (r2104281802)
Copyright (c) 1999-2021, https://harbour.github.io/
Posts: 10733
Joined: Sun Nov 19, 2006 05:22 AM
Re: Usar o no variables publicas.
Posted: Thu Mar 25, 2021 01:45 PM

Code:

FUNCTION GetWndMain()
RETURN oWndMain  
 

and in the module that I have to use it.
Code:

oWndMain := GetWndMain()
 


BTW,
We can use the built-in FWH function
Code (fw): Select all Collapse
WndMain()

anywhere in the application, without creating our own function GetWndMain()
PS: I know this is not the main purpose of this topic.
Regards



G. N. Rao.

Hyderabad, India
Posts: 2706
Joined: Fri Oct 07, 2005 01:50 PM
Re: Usar o no variables publicas.
Posted: Thu Mar 25, 2021 01:49 PM

To All

I only use Publics for defining System wide user roles .. Read, Write, Supervisor and Admin... Statics work fine in a .prg with many functions .. specifically if you need to update a Static value within your .prg and have visibility within the .prg ..Hash's works great if you want to pass locals and update locals with visibility in other functions that have multiple .prgs.

My choice is to always use locals .. even statics need to be released with nil .. with locals .. use them and pass them as a value only .. I also believe Locals execute faster at run-time.

Rick Lipkin

Posts: 1956
Joined: Fri Oct 07, 2005 07:08 PM
Re: Usar o no variables publicas.
Posted: Thu Mar 25, 2021 02:29 PM

I need to save values that I can access from any of the classes I have. And I don't know how to do it, I have already tried several examples.

FWH 21.02
Harbour 3.2.0dev (r2104281802)
Copyright (c) 1999-2021, https://harbour.github.io/