Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations Chris Miller on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

How to declare a variable in VFP? 3

Status
Not open for further replies.

greathope123

Programmer
Nov 1, 2011
84
GB
In Command3.Click
local userName
userName="abc"
?userName
Why it did not print out "abc"?

It printed something in database table1 because "username" is its field name?
My question would be how to tell VFP a variable is the field name in database table or is a variable I declared in "local"?
 
Craig,

Thanks - I never do that. It's not necessary, and like Mike says, it's just wrong!

Bill
 
Hi,

a fine tool to correct you have correctly placed m. is to be found in Thor: "Add MDots to variable names" but be sure to enable the "Use mDots only where required" checkbox.

Jockey(2)
 
This article talks about work areas and aliases and so forth:


BTW, put me in the "use mdots wherever they're called for" camp. I've spent too much time debugging code that failed because mdots weren't used. Even if you declare a naming convention, you can't assume that everyone else you need to share code with will obey.

Tamar
 
Tamar,

As one of the most respected VFP folks I gave heard of (and read many times), I would like you to clarify something for me based on what you posted.
If I am assigning a value to a memvar I don't use the "m." ..

lcFname = SPACE(20) or
lcFname = customers.fname

.. because it can't be anything other than a memvar that I am storing a value to. Are you saying you would do this?:
m.lcFname = SPACE(20) or
m.lcFname = customers.fname

Note I am one who does use the "m." everywhere else though so I know if it's a memvar that I am referring to. My experience is that it's faster as well.

Bill


 
Hi,

you are not supposed to do:

m.myVariable = myTable.myField

apart that it is superfluos, afterall myVariable can only be a variable in this case and not a field, it will also slow your application. I am absolutely sure you will never ever be able to notice if this is the one and only line like that in your app but 100000 of these could give a difference.
Anyway just prepare your coding as you would like, with or without the m.Dot and than have the mDot tool from Thor correct it for you.

Regards,

Jockey(2)
 
Thanks for pointing to the Thor option.

Well, OK, one of the detail reasons, why I stopped working on parsing code to add mdots is, because of corner cases, where you can't tell, if a field is meant or a variable. It's easy to parse for LOCAL variable definitions and add m., it's just a search&replace, you can also easily avoid the var=expression case, but you never know, if a name you encounter not declared LOCAL is a private variable or a field name. Now you can say don't use private variables, but they accelerate recursive operations far more, than mdot, because you don't need to pass private variables on and you don't have an indirectly declared variable by lparameters on each recursion level.

And if you care about the last bit of percentages on performance, then also use STORE instead of = as assign operator.

Here's what I measured:
empty loop, 10 million iterations: 0.691 seconds
loop with 20 = assignments per iteration, 10 million iterations: 51.897 seconds
loop with 20 store assignments per iteration, 10 million iterations: 39.827 seconds

corrected loop body durations:
loop with 20 = assignments per iteration, 10 million iterations: 51.897 seconds - 0.691 seconds = 51.206 seconds
loop with 20 store assignments per iteration, 10 million iterations: 39.827 seconds - 0.691 seconds = 39.130 seconds

And that means store needs 39.130/51.206 = ca. 0.76 of the time of = assignment or = assignment takes 51.206/39.130 = ca 1.31 of STORE assignment.

But I also see no code samples making extensive use of STORE, it's like mdot, neglectable for the single assignment, but not in a tight loop.

Tamar has the only real valid point in my eyes, not knowing what names come from outside, that can bite you, I already gave a solution to that, introduce obfuscation, which for example means changing all your variable names to lengthy random strings, that won't crash with field names, it's quite easy introducing some defines, eg #DEFINE loRange djksd344hfjkdhdjkshfjsdfhsd5454khfjk234dsjkfsdj5623kfjhsdfhkdshf, for example, now the field name to make such a case of matching names would need a table with a djksd344hfjkdhdjkshfjsdfhsd5454khfjk234dsjkfsdj5623kfjhsdfhkdshf field. Besides that define, your code still has the loRange variable name and you can read it just normal.

In case you also need to address a field name lOrange, if you know that in advance, you avoid loRange as variable name, if you work on any other developers database with generic tools, like eg gendbc you read file names via AFIELDS for example, and then have names read in at runtime, use them with macro substitution, and they won't be redefined by #DEFINE. Also, defines don't change strings, eg you can have code like lcField = "lOrange", then &lcField and this stays lOrange, despite of the #DEFINE.

My and Tamar's experiences about how many times a random match of field and variable names occurred, differ very much, which may just be, because I have more control about my environment in terms of tables, naming convention and also table widths, in regard of the performance degradation being low. If you're at the point you can quench the last bit of acceleration out of mdot, you should perhaps go to other programming languages. The advantage of VFP is not performance but rapid development and easier maintenance, shorter code because of less atomic single commands, VFP really is a high level language in the data centric domain, which is it's main advantage. But in fact it's object code much compares to java p-code and is therefore not compiled for a cpu, but read by the runtime and thus VFP is an interpreter. If you want performance go C++, but for a weighed optimum of rapid develop and fast performance SQL Server and DotNet are the defacto standard for Windows, not VFP anymore.

Bye, Olaf.
 
Wtotten- As Jockey2 said, you don't need mdot on the left side of an assignment. When I wrote "use mdots wherever they're called for," I meant specifically anywhere where there could be ambiguity. No ambiguity on the left side of an equals sign (including in FOR loops), so no need for mdot.

Olaf-My take on this is that using mdots is going with the flow and using VFP the way it was intended to be used. Complicated schemes to avoid the need for mdots are just work-arounds. It's much easier to just use mdots.

FWIW, I didn't for the first very long time that I worked with FoxPro. Eventually, I got tired of fighting and discovered that I could very quickly get used to both reading and writing mdots. (In fact, today, I'm far more likely to put an mdot where I shouldn't--in front a field name, say--than to fail to put one where I should.) As for readability, which is an argument I hear a lot, I think you get used to it pretty fast.

Tamar
 
I don't think putting m. on the left of an assignment is wrong. It works, therefore it's right. I've said for years, "If the code gives the correct answer, the code is correct. It may not be optimal, but it is correct."

Craig Berntson
MCSD, Visual C# MVP,
 
Hi Olaf,

The use of m.Dot is widely ciritized as it would not benefit from any time-gain. Which is theoreticaly not true but practicaly very true. m.Dot is not primarely to be used for speed purpose but more important to make your code truly generic, the speed issue is just an unnoticable side effect.
Just once in your life time when you worked with a legacy application, not coded with m.Dot on which you made an extension/update and you will experience an error due to this, you will be convinced. Most probably due to the fact that mostly those errors are not caught by your clever error-catching device, the application simply gives a wrong unexpected result.
My motto for a couple of years,- after such an experience, it took me more than a working day to solve (at that time Thor with m.Dot did not yet exist) - The absense of the use of m.Dot qualifies your application 'for recreational use only'

Regards,

Jockey(2)

P.S. don't hope this will end up in a 100+ opinions thread.
 
BeatDeadHorse.gif


Sorry, I just couldn't help myself. [bigsmile]

-Dave Summers-
[cheers]
Even more Fox stuff at:
 
"If the code gives the correct answer, the code is correct. It may not be optimal, but it is correct."

I'd agree with this with the addition of one critical word: reliably. The code must reliably give the correct answer.

I'm dealing with a boatload of code I didn't write, in an organization where all the developers have left, and there's a lot of code that gives the right answer when the moon is full and the tidal pull is just right. But let one condition go wobbly and the whole thing spins off its center! (And can you guess how often one condition goes wobbly? <g>)
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top