object/property1: "new value"
[1/6] from: hk:readysoft at: 29-Jan-2001 12:17
Hi list, 1) how can I forbit to change values in an object? 2) how can I get an event, when an object variable is changed? In Visual Basic and VBScript I can do it with: Property get variable1() ... end Property Property let variable1(new) ... End Property Many Thanks Helmut
[2/6] from: rebol::techscribe::com at: 29-Jan-2001 11:32
Hi Helmut, REBOL has a protect function that protects words from being reassigned. The protect function does not work for words that are implemented in objects. I have previously asked RT to add this functionality. As of the latest experimental /Core release this feature has not been added. Elan Helmut Knoblauch wrote:
[3/6] from: gjones05:mail:orion at: 29-Jan-2001 14:27
Hi Helmut, Elan seems to have answered your first question that pertains to protecting attributes in objects. I am not sure that I fully understand what you are asking in your second question: ...
> > 2) how can I get an event, when an object variable is changed?
... Maybe an example will help. Here is an object with attributes and functions taken from: http://www.rebol.com/rebolsteps.html account: make object! [ name: "Flintstone" balance: $100 ss-number: #1234-XX-4321 deposit: func [amount] [balance: balance + amount] withdraw: func [amount] [balance: balance - amount] ] Are you asking how to "fire" an event if an attribute, such as 'balance, is changed? Or are you asking how to get and set the attribute? Or are you asking something else entirely? --Scott
[4/6] from: hk:readysoft at: 30-Jan-2001 9:29
Hi Scott, I want to get a "fire" -event if an attribute, such as 'balance, is changed. So I can test of a valid data-type or to test wether the new value is in a valid range. Additional, I want to prevent someone from changing the 'withdraw or 'deposit functions. And my next question is, how can I define private attributes in an object? (like in Java) -helmut -----Ursprüngliche Nachricht----- Von: GS Jones <[gjones05--mail--orion--org]> An: [rebol-list--rebol--com] <[rebol-list--rebol--com]> Datum: Montag, 29. Januar 2001 21:39 Betreff: [REBOL] Re: object/property1: "new value"
[5/6] from: gjones05:mail:orion at: 30-Jan-2001 7:34
Helmut, thank you for the additional clarification. First, let me caution that I am still a novice with REBOL. I am certain that there are others on this list that could answer your question with more authority than myself. However, since no one has yet addressed your second question in the original email, I'll give it a try. Excerpted from Helmut's message ...
> I want to get a "fire" -event if an attribute, such as 'balance, is > changed. So I can test of a valid data-type or to test wether the new
> is in a valid range. > >Additional, I want to prevent someone from changing the 'withdraw or >'deposit functions. > >And my next question is, how can I define private attributes in an object? >(like in Java)
... 1) Testing for valid data-type: REBOL allows one to define an additional field in function calls that identifies the data types. In the "REBOL/Core User Guide" (page 253), the Arg Type is: "A block that identifies the data types that are accepted by the function. If a data type not identified in this block is passed to the function, an error will occur." In our example object definition, the deposit and withdraw functions can be modified to only accept the money! type. account: make object! [ name: "Flintstone" balance: $100 ss-number: #1234-XX-4321 deposit: func [amount [money!]] [balance: balance + amount] withdraw: func [amount [money!]] [balance: balance - amount] ] The argument "amount" must now be of the type money!. If the function is called with the incorrect data-type, then an error is generated that specifically identifies what data-type is required. 2) Testing whether the new value is in a valid range: If I understand this aspect of your question, it seems to me that this may be more of a "business rule" specification that can then be enforced through the program logic of the function methods. For example, one bank may not allow for an "overdraft" (meaning, the bank doesn't allow the balance to drop below zero dollars or deutschmarks, as the case may be ;-). In this case, then the withdraw function would need to check the "business rule" and throw an error if the rule is violated. Another bank may allow for the balance to drop to -$100.00, in which case the business rule would need to be a little different. This general approach is demonstrated with a code sample (from the User Guide with slight alteration): bank-account: make account [ withdraw: func [amount [money!]] [ either negative? (balance - amount) [ print ["Denied. Inadequate funds to withdraw " amount] ][ balance: balance - amount] ] ] Perhaps Elan or someone else could comment on the best way to most effectively throw errors from within functions. I have little knowledge of this in REBOL. 3) Firing events/ checking events: Here I am treading on thin ice (knowledge-wise) again, but REBOL/Core doesn't seem to have a automatic event loop. It does support events in regard to port access and management. REBOL/View, of course, utilizes an event loop, which allows more flexibility in throwing an event and then processing events. These aspects seem little different than any language with which I have delt, so I do not see this as any sort of deficiency, per se. Of course, one can set up an event loop that then allows for events to be checked, depending on the needs of the program. 4) Protecting against the changing methods in objects and making attributes private: As Elan wrote yesterday, REBOL does not have a "protect" feature within functions that protects methods and attributes. REBOL seems to allow encapsulation but not hiding (at least at the source code level in a non-distributed application environment --- writing the application in a distributed manner would allow for method and attribute hiding, thereby getting around this "limitation"). I hope that this information helps to answer your questions. Others may be able to tell you more specifics on some of these areas. Please let me know if I have misunderstood something. --Scott
[6/6] from: dockimbel:free at: 30-Jan-2001 16:21
Hi Helmut, [...]
> I want to get a "fire" -event if an attribute, such as 'balance, is > changed. So I can test of a valid data-type or to test wether the new value > is in a valid range.
Define a 'set-balance (or 'let-balance) function in the account context, where you can put all your processing code. For example : account: make object! [ balance: $100 set-balance: func [value][ ...process value and assign 'balance to value if ok... ] ... ] So, when you want to modify 'balance somewhere in your script do : set-balance value instead of balance: value In VisualBasic, it's the same thing except that VB will automatically call the Let property when it encounters a "=" symbol. If you don't like this solution, you can try another way by using the 'query function. For example, query/clear account will return you a block of modified words in 'account (else 'none). With this function, you can know what words have been modified in an object context and then do the appropriate actions. HTH, DocKimbel.