Alaska Software Inc. - SET SCOPE TO and SKIP
Username: Password:
AuthorTopic: SET SCOPE TO and SKIP
Nevzat KanburSET SCOPE TO and SKIP
on Tue, 03 Mar 2020 16:24:52 +0300
Hi,

In the following code when I use SKIP it only changes the first correct 
record and when I use GO TOP it changes all the matching records 
(correct action)

Why SKIP does not work corrcetly here?
Should it SCOPE stay in the range?

Any help please?


function 
;renk_zupd(cxData,cRkodu,cRenk,cDenye,cUKodu,cUUnvani,cKodux,cUnvanix,cAlias)

SET SCOPE TO cxData   Old value
GO TOP

do while !eof()
    if rlock()
       REPLACE RKODU       WITH cRkodu,;
	      RENK        WITH cRenk ,;
	      DENYE       WITH cDenye,;
	      &(cKodux)   WITH cUKodu,;
	      &(cUnvanix) WITH cUUnvani
       UNLOCK
    endif
    GO TOP    Changes all records (correct action)
    //SKIP    Changes ony first mathing record.
enddo

dbCommitAll()

SET SCOPE TO
GO TOP

return nil
Edgar Borger Re: SET SCOPE TO and SKIP
on Tue, 03 Mar 2020 11:35:03 -0300
What is the key (index) to the file ?
if you replace the key field, and the skip, it is going to look on the next record in the index and not in the file, so depending on your replace, it 
will reach eof.

for this to work with skip, you cannot replace the index key field ! (or do no use an index)

regards,
Edgar



Em 03/03/2020 10:24, Nevzat Kanbur escreveu:
> Hi,
> 
> In the following code when I use SKIP it only changes the first correct record and when I use GO TOP it changes all the matching records (correct action)
> 
> Why SKIP does not work corrcetly here?
> Should it SCOPE stay in the range?
> 
> Any help please?
> 
> 
> function ;renk_zupd(cxData,cRkodu,cRenk,cDenye,cUKodu,cUUnvani,cKodux,cUnvanix,cAlias)
> 
> SET SCOPE TO cxData   Old value
> GO TOP
> 
> do while !eof()
>     if rlock()
>        REPLACE RKODU       WITH cRkodu,;
>            RENK        WITH cRenk ,;
>            DENYE       WITH cDenye,;
>            &(cKodux)   WITH cUKodu,;
>            &(cUnvanix) WITH cUUnvani
>        UNLOCK
>     endif
>     GO TOP    Changes all records (correct action)
>     //SKIP    Changes ony first mathing record.
> enddo
> 
> dbCommitAll()
> 
> SET SCOPE TO
> GO TOP
> 
> return nil


Edgar Borger
Softsupply Informatica Ltda.
Rua Alagoas, 48
Sao Paulo, SP
01242-000
Tel   : (5511) 3159-1997
Email : softsupply@terra.com.br
Andreas Gehrs-Pahl
Re: SET SCOPE TO and SKIP
on Tue, 03 Mar 2020 13:49:41 -0500
Nevzat,

As Edgar already explained, changing the fields that comprise the index and 
are referenced in the scope will not work with a simple skip, as the record 
pointer is moved to EoF() as soon as you change the record, as it no longer 
falls within the Scope after the change.

A simpler code pattern would be to just use Seek instead of a Scope and Skip 
or Go Top:

* The code below assumes that "cAlias" is the actual, correct Alias!

Function renk_zupd(cxData, cRkodu, cRenk, cDenye, cUKodu, cUUnvani, ;
                   cKodux, cUnvanix, cAlias)
   while (cAlias)->(DbSeek(cxData))
      if (cAlias)->(DbRLock())
         (cAlias)->RKODU := cRkodu
         (cAlias)->RENK  := cRenk
         (cAlias)->DENYE := cDenye
         (cAlias)->(FieldPut(FieldPos(cKodux),   cUKodu))
         (cAlias)->(FieldPut(FieldPos(cUnvanix), cUUnvani))
         (cAlias)->(DbUnlock())
      endif
   enddo
   (cAlias)->(DbCommit())
   (cAlias)->(DbGoTop())
return (NIL)

Hope that helps,

Andreas

Andreas Gehrs-Pahl
Absolute Software, LLC

phone: (989) 723-9927
email: Andreas@AbsoluteSoftwareLLC.com
web:   http://www.AbsoluteSoftwareLLC.com
[F]:   https://www.facebook.com/AbsoluteSoftwareLLC
Jim LeeRe: SET SCOPE TO and SKIP
on Wed, 04 Mar 2020 00:15:43 +0100
hi,

> SET SCOPE TO cxData   Old value
> GO TOP

instead of GO TOP i recommend to use SEEK( cxData ) to be sure that you
SCOPE have matching any data



---
Diese E-Mail wurde von AVG auf Viren geprüft.
http://www.avg.com
Nevzat KanburRe: SET SCOPE TO and SKIP
on Wed, 04 Mar 2020 11:24:16 +0300
4.03.2020 02:15 tarihinde Jim Lee yazdı:
> hi,
> 
>> SET SCOPE TO cxData   Old value
>> GO TOP
> 
> instead of GO TOP i recommend to use SEEK( cxData ) to be sure that you
> SCOPE have matching any data
> 
> 
> 
> ---
> Diese E-Mail wurde von AVG auf Viren geprüft.
> http://www.avg.com
> 
Thank you

I know ;
do while dbseek(cKey) .and. !eof()
works fine.
But I want to know why when I use SCOPE and SKIP does not work.
As I know after first seek than SKIP pointer should go to the next 
record not to the eof.
Am I right?

I don't have any problems with index keys ont etc.

rgds,
Nevzat
Edgar Borger Re: SET SCOPE TO and SKIP
on Wed, 04 Mar 2020 10:23:17 -0300
Hi Nevzat,

small example:
if you have records like

001
002
005
015
023
035
048
065

if you go to record 015, and change its key to 075, it will automatically be positioned as last record, so when you SKIP, you hit eof()

I hope that clarify

regards,
Edgar


Em 04/03/2020 05:24, Nevzat Kanbur escreveu:
> 4.03.2020 02:15 tarihinde Jim Lee yazdı:
>> hi,
>>
>>> SET SCOPE TO cxData   Old value
>>> GO TOP
>>
>> instead of GO TOP i recommend to use SEEK( cxData ) to be sure that you
>> SCOPE have matching any data
>>
>>
>>
>> ---
>> Diese E-Mail wurde von AVG auf Viren geprüft.
>> http://www.avg.com
>>
> Thank you
> 
> I know ;
> do while dbseek(cKey) .and. !eof()
> works fine.
> But I want to know why when I use SCOPE and SKIP does not work.
> As I know after first seek than SKIP pointer should go to the next record not to the eof.
> Am I right?
> 
> I don't have any problems with index keys ont etc.
> 
> rgds,
> Nevzat


Edgar Borger
Softsupply Informatica Ltda.
Rua Alagoas, 48
Sao Paulo, SP
01242-000
Tel   : (5511) 3159-1997
Email : softsupply@terra.com.br
Andreas Gehrs-Pahl
Re: SET SCOPE TO and SKIP
on Wed, 04 Mar 2020 12:01:30 -0500
Nevzat,

>But I want to know why when I use SCOPE and SKIP does not work.
>As I know after first seek than SKIP pointer should go to the next 
>record not to the eof.
>Am I right?

No, you aren't right.

If you set a Scope -- which requires an Index -- then you limit the records 
that you can reach with Go Top, Skip and Go Bottom to the records that are 
within that Scope.

In your code, you set the Scope (Top and Bottom) to a value contained in 
"cxData". So, to be in the Scope, the Field(s) that make(s) up the Index Key 
must have the value of "cxData" to be seen.

You then use Go Top to select the first record (in the Scope) with that 
Index Key value, which is basically the same as using Seek cxData. If you 
haven't reach EoF() -- meaning that there are records with this Index Key in 
the table -- then you enter your While loop.

Then you lock the current record and (apparently) change the Field(s) that 
contain the Index Key, using Replace, and unlock the record. The moment you 
do the Replace, the Index Key changes, and the Record is no longer part of 
the Scope and is re-ordered somewhere else in the Index Order. As the record 
isn't part of the Scope anymore, it is beyond EoF() as far as the Scope is 
concerned.

Because of that, if you skip from that Record to the next one, the following 
EoF() test will be TRUE, as the selected Record is not part of the Scope, 
and your While loop is exited (after the first replace).

This is a very basic rule: Never change the Index Key in a loop that is 
controlled by that Index Key (Scope or no Scope, but especially if you use 
a Scope)!

I recommend you use the Debugger and look at the record pointer, previous 
and following Record (in Index Order), and EoF/BoF, while stepping through 
your code.

Hope that helps,

Andreas

Andreas Gehrs-Pahl
Absolute Software, LLC

phone: (989) 723-9927
email: Andreas@AbsoluteSoftwareLLC.com
web:   http://www.AbsoluteSoftwareLLC.com
[F]:   https://www.facebook.com/AbsoluteSoftwareLLC
Nevzat KanburRe: SET SCOPE TO and SKIP
on Wed, 04 Mar 2020 11:27:21 +0300
4.03.2020 02:15 tarihinde Jim Lee yazdı:
> hi,
> 
>> SET SCOPE TO cxData   Old value
>> GO TOP
> 
> instead of GO TOP i recommend to use SEEK( cxData ) to be sure that you
> SCOPE have matching any data
> 
> 
> 
> ---
> Diese E-Mail wurde von AVG auf Viren geprüft.
> http://www.avg.com
> 
Again the following is working fine

SET SCOPE TO cKey
GO TOP

do while !eof()
    ....
    ....
    GO TOP (instead of SKIP)
enddo

SET SCOPE TO
GO TOP

RGDS
Carlos A Beling Re: SET SCOPE TO and SKIP
on Wed, 04 Mar 2020 09:42:48 -0300
Hi Nevzat:
good morning.
I always use INDEX ON FOR ... and it works great and is very fast.
But if you change the contents of the field in the index you must to go 
to the top of the file. Among other possible things this is because the 
new one index key may to be less than the current one.

Fraternally
Beling

On 03/03/2020 10:24, Nevzat Kanbur wrote:
> Hi,
> 
> In the following code when I use SKIP it only changes the first correct 
> record and when I use GO TOP it changes all the matching records 
> (correct action)
> 
> Why SKIP does not work corrcetly here?
> Should it SCOPE stay in the range?
> 
> Any help please?
> 
> 
> function 
> ;renk_zupd(cxData,cRkodu,cRenk,cDenye,cUKodu,cUUnvani,cKodux,cUnvanix,cAlias) 
> 
> 
> SET SCOPE TO cxData   Old value
> GO TOP
> 
> do while !eof()
>     if rlock()
>        REPLACE RKODU       WITH cRkodu,;
>            RENK        WITH cRenk ,;
>            DENYE       WITH cDenye,;
>            &(cKodux)   WITH cUKodu,;
>            &(cUnvanix) WITH cUUnvani
>        UNLOCK
>     endif
>     GO TOP    Changes all records (correct action)
>     //SKIP    Changes ony first mathing record.
> enddo
> 
> dbCommitAll()
> 
> SET SCOPE TO
> GO TOP
> 
> return nil