Page 2 of 2

PostPosted: Wed Aug 29, 2007 3:00 pm
by James Bott
Ehab,

>Could you please help in syntax.

I'm not sure what syntax you mean. Did you mean making a browseDelete() method? If so, you just define it in your class definition and name the method--just the same as the current delete() method you have. Actually, you can just rename it in both places.

Code: Select all  Expand view
class ... from TData
   ...
   method BrowseDelete()
endclass

method BrowseDelete()
   ...
return self


OK, you may be cofused about the way the current delete method is defined. Because "delete" is a reserved word, we have to use a special way of defining it. This is only used for reserved words.

Code: Select all  Expand view
class ... from TData
   message delete method _delete
endclass

method _delete()
...
return self


James

PostPosted: Wed Aug 29, 2007 9:04 pm
by Ehab Samir Aziz
Oka I did it in such a way but about calling the two methods ?
Code: Select all  Expand view
//--- meter class
class Tmeter from TData
   method new
   method browser
   method add
   method edit
   message delete method BrowseDelete
Hidden:
   data lAdd as logical
endclass

//--- meter class
class Tmeterdelete from TData
     method new
     method browser
     method add
     method edit
     method DBFdelete   
   Hidden:
     data lAdd as logical
endclass
 

..

method BrowseDelete(oBrw,oMeter)
   ::skip(1)   
   ::skip(0)   
if oBrw:eof()
   ::skip(-1)   
   ::skip(0)   
endif
oBrw:refresh()   
   

return self

//---------------------------------------------------------------------------//

method DBFdelete(oMeter,oBrw)
local nRecno

   if msgYesNo("Delete this record?") 
      super:delete()
   endif


nRECNO := oMeter:RECNO()
   oMeter:pack()
GOTO nRECNO

return self


PostPosted: Wed Aug 29, 2007 9:23 pm
by James Bott
Ehab,

No, it is much simpler.

Code: Select all  Expand view
//--- meter class
class Tmeter from TData
   method new
   method browser
   method add
   method edit
   method BrowseDelete
Hidden:
   data lAdd as logical
endclass

..

method BrowseDelete(oBrw,oMeter)
   if msgYesNo("Delete this record?") 
      ::delete()
   endif 
   ::skip(1)   
   ::skip(0)   
   if oBrw:eof()
      ::skip(-1)   
      ::skip(0)   
   endif
   oBrw:refresh()   
return self


Keep in mind that this is a table class (we call them DBFs) so a browse function (method) doesn't really belong in this class, but we are doing it because it is easier than adding it to the TXBrowse class. You don't want to mess with the table delete method and it shouldn't have any interfaces in it--you may want to call it from other code (as we did above in the BrowseDelete() method).

Also you don't ever want to change the name of the method (like DBFDelete) because you want all tables to have a delete method (called "delete"). This is one of the basics of using OOP and it allows you to do things like pass any object and call the delete method. If each object had a different name for the delete method then you would have to code a large DO CASE statement and add to it for each new object--not good. You can't do this with procedural coding.

Code: Select all  Expand view
function whatever( oObject )
    oObject:delete()
return self


Also you do not need a new class for a new method. The method is part of the existing class--in your case TMeter.

See OOP is really simple.

James

PostPosted: Thu Aug 30, 2007 4:38 am
by Ehab Samir Aziz
Where in code can I pack the deleted records and in same time keep the existing browse as BrowseDelete(oBrw,oMeter) ? I f packed the shape of the browse is going to be redisplayed aganist BrowseDelete(oBrw,oMeter).
Thanks

PostPosted: Thu Aug 30, 2007 5:05 am
by James Bott
Ehab,

You cannot pack a data file while it is being used. It must be in exclusive use and it takes way too long. My suggestion as before is to reuse records. Or, you can pack during reindexing which also requires exclusive use.

When you delete records with SET DELETED ON, they will be invisible so there is no need to pack. Also when you when you index you should always use the FOR NOT DELETED() clause so the index record count will not include deleted records.

James

PostPosted: Thu Aug 30, 2007 1:53 pm
by Ehab Samir Aziz
Any way to delete and pack at the same time beside keeping the browse as BrowseDelete() do ?

PostPosted: Thu Aug 30, 2007 1:58 pm
by James Bott
Ehab,

>Any way to delete and pack at the same time beside keeping the browse as BrowseDelete() do ?

Did you read my previous message? No, you cannot pack a file after deleting a record, nor would it be practical even if you could. This has nothing to do with the browse delete method--you can't do it using any method or function.

James

PostPosted: Sat Sep 01, 2007 3:46 pm
by Ehab Samir Aziz
No harm fom putting pack after using the file like below or you think there is a better place to for the pack for the deleted commands :
Code: Select all  Expand view
use mete exclusive
    index on me_mc_serl to mete
    index on me_date to mete2
    pack
    use
   

PostPosted: Sun Sep 02, 2007 1:06 am
by James Bott
Ehab,

No you don't want to do it that way either. What if the database has a million records? Every time the user opens the file it is going to get packed which could take a half hour.

You have to pack databases using a separate routine that the user can call occassionally. You can leave deleted records in the database for quite some time unless you are deleting lots of them and if you doing that you need to rethink the design.

Still the best solution is to reuse deleted records. Then you never have to PACK.

James