Object paradigm: message passing

  • Thread starter 0rthodontist
  • Start date
In summary, I don't think Java or Smalltalk really model true "message passing" between objects; function calling instead seems to be more accurate. Pure message-passing languages like the one described have some disadvantages, such as being extremely verbose and requiring a lot of context to be sent with data.
  • #1
0rthodontist
Science Advisor
1,231
0
I've been thinking about the object paradigm, more specifically the claim that method calling represents "message passing" between the objects. At least in Java, (and also, according to Wikipedia, in Smalltalk) this doesn't seem strictly true to me; it seems more like function calling than actually delivering a message. A true message passing framework should be something like this:
1. Object A receives a message from object B containing some information X about the state of the universe, call it U.
2. On receiving X, Object A takes some action, or takes no action, as it pleases.
3. Object A may pass a message back to object B, or to any other objects it likes. This message contains some information Y about the universe U, perhaps new information that object A generated, or maybe existing information.

This does not seem like it strictly translates into object B calling a method in A and getting a return value back. If the process of B sending a message to A is a method call, the process of A sending information back to B should also be a method call. A should call another method in B to give the "return value" to B; methods should not have a "return value" per se. At least, that's what it seems like a strict interpretation of the "message passing" paradigm would claim.

How about a "pure message-passing" language like the following:
  1. There is one global procedure, built into the language, called Send(D, B) that sends data D to object B. This procedure represents, abstractly, any communication media between the objects.
  2. Each object has a method Receive(D, A) that specifies what should be done when data D is received from object A. Receive is not directly callable from anywhere. Calling Send(D, B) from A has the effect of calling Receive(D, A) in B.
  3. There is a universal language for describing any data to be sent--data should be viewed as true statements about the universe rather than "arguments to a function." XML looks like a good candidate. Validation that the data takes a correct form is essential, and ideally the data contained in any message passed between any two objects would agree with the data contained in any message passed between any other two objects--this is because the data should represent truth about the universe, not just 'input.'
  4. Each object can then have a bunch of other local functions and local data that it uses itself. One that might be useful as part of the language is Get(x), which extracts data from the set of all truths that the object currently knows.
For example if you have a calculator object, you might, from class A, tell it something like
Code:
D =
<universe>
<circle ID=10>
<radius>3.0</radius>
<area>unknown</area>
</circle>
<universe>
Send(D, calculator) // now calculator will validate and parse the new information that A wants to know the radius of circle 10, and send back to A some XML stating the area of the circle
this.Get(<universe><circle ID=10><area>areaof10</area></circle></universe>)
Send(areaof10, ScreenOutput)
Then the screen would display something like 28.27

Disadvantages?
  • Extremely verbose compared to most languages. This is a big one.
  • Figuring out what context information should be provided with a message could be problematic. In this example, I tried to identify the circle as "10," which would probably lead to a conflict quickly. If it were to work in real life, there would have to be a symbol generator (like Lisp's gensym) to give objects unique ID's.
  • Sending so much context for a piece of data is inefficient. This problem can probably be optimized significantly at runtime by replacing tags with numeric characters, since all the objects would be aware of the single valid grammar for the program's data.

Advantages?
  • Self-documenting, human-readable input and output between objects, since XML is nearly self-documenting.
  • The abstraction of messages as "true" data about the universe. Tracking down a bug would be reduced to manually reading through the messages that were passed between objects, and determining when they are true and when they become false. The first time a message is passed that is false, the bug was in the object that generated it. Also, this is somewhat similar to the functional programming paradigm; functions in a functional language can be viewed as "universally true" statements about some data. For example sum [1..40] represents the absolute, universal piece of data which is the sum of the numbers from 1 to 40, and is stateless and will never change. Similarly in this example, areaof10 in <universe><circle ID=10><area>areaof10</area></circle></universe> represents the area of the lone circle in the universe whose ID is 10, which is a theoretically absolute value and won't ever change.
  • I think it represents a true "message-passing" programming framework more closely than ordinary languages, which might be interesting to see.


By the way, I don't like being grumpy. Please just don't reply if nothing about this interests you.
 
Last edited:
Technology news on Phys.org
  • #2
It sounds like you've invented CORBA, or perhaps SOAP. Congratulations.

Honestly, I fail to see how a method call is not exactly equivalent to your 1-2-3 steps for passing a message.

1. Object A receives a message from object B containing some information X about the state of the universe, call it U.

When you call another object's method, you pass it some arguments. The arguments, together with the method which was called, comprise the "message."

2. On receiving X, Object A takes some action, or takes no action, as it pleases.

The method certainly takes some action, or does no action, as it pleases.

3. Object A may pass a message back to object B, or to any other objects it likes. This message contains some information Y about the universe U, perhaps new information that object A generated, or maybe existing information.

An object's method may return a value, and it may call other methods in other objects.

The only difference in your "pure message passing" paradigm, truly, is that you have abstracted away the concept of the method name being part of the message. Instead, you just use some general-purpose send() method, and the receiving object looks at the payload and decides what to do with it. In general, it'll just look up a method in a list and dispatch it. All you've accomplished is forcing every object to explicitly include such a runtime dispatch table, rather than letting the compiler perform the same function at compile-time. You add overhead and ambiguity and get little in return.

There is, of course, no reason why you could not implement this behavior all you'd like in any object-oriented language already in existence, so I don't see the justification for a new language.

Keep in mind that there are very good uses for things like XML, but, in general, the passing of tiny messages of the sort normally seen in well-constructed object-oriented programs does not require such flexibility. You'd be talking about an order of magnitude (or more) decrease in performance.

If you want to see a well thought-out message-passign paradigm, look into the "signals and slots" mechanism built into the graphical toolkit Qt. It is, in fact, based on method calls, but it includes a level of run-time abstraction that makes such method calls appear like pure message passing.

- Warren
 
  • #3
These are what I think are the important things about it, as distinguished from standard OOP:
  1. The Send(D, B) method has no return type. Data is returned via Send()ing it, which is more similar to message passing than having a special mechanism to return() the data. Returning data is just the special case of Send()ing data where the target happens to be the same object that provided some data.
  2. All data passed is human-readable and possibly more debuggable
  3. It is used to generate true statements--in that sense it is a logic programming language like Prolog. It is like a logic programming language where facts are not represented in a single knowledge base (KB) but are distributed into the KB's of the various objects, where a particular object does not necessarily store all of the universe's information at a given time. Although it is also very different from logic programming in that it doesn't necessarily have sophisticated automatic inference mechanisms. (though it might, within the individual objects)
  4. The "unknown" entry in the circle area example, which might be replaced by a question mark or some other reserved symbol, indicates unknown data. A target object would typically try to fill in as many unknowns as possible. Therefore one Send(D, B) might get back 10 additional previously unknown pieces of data, or 7 of them, or none, depending on how much data B has at the current time--B will typically fill in as many unknowns as it knows how to, which is another way that Send() differs from an ordinary method call.

This is the difference from OOP that I think is not as important:
  • The specific singular "Send" function. Ordinary method calls would serve just as well, so long as they passed "truthful data" instead of just raw input back and forth and did not have return types.
Hopefully all this is a clearer statement and addresses some of what you said.


Thank you for pointing out SOAP to me; it is somewhat similar.

I'm not sure about "signals and slots." It looks like I need to be affiliated with some organization to get a trial version of Qt. The Wikipedia article on "signals and slots" says that it is similar to the observer design pattern. Are the signals and slots auto-generated in a GUI?

An order of magnitude performance hit is nothing unreasonable, since logic programming languages and interpreted languages can be slower by several orders of magnitude without crippling them. But I think that what I'm describing would not have to be much slower since all parts of the application know the entire syntax for any data being passed. You'd just compile all XML into hash maps from ID's to entries. For example the ID of a radius of circle #10, namely <universe><circle ID=10><radius>2.0</radius></circle></universe>, might be 458. So you have the pairing (458, 2.0), which any object in the program knows. Using a translation tool back to XML, a human could still read the data as if it were just plain text. Looking something up in a hash map is a bit slower than popping off an argument from the stack, but is it that much slower? And passing messages is only 1 part of the program--you would expect most of the work to take place inside the objects, which could be written in C with assembly code for the tricky parts for all I know.
 
  • #4
Okay, so start using methods with no return types. Knock yourself out.

Human-readable data types may be more "debuggable," but I'd venture that they're also more susceptible to bugs in the first place. The more decisions a method has to make (Do I have piece of data A? Is it comprehensible? Do I have piece of data B? Is it comprehensible?), the more likely some of those decisions will be coded incorrectly.

Qt has an open-source version which can be freely downloaded. You just can't use it in commercial (closed-source) applications. Its signals and slots mechanism is actually a layer on top of C++. It actually adds a couple of additional modifiers and keywords to the C++ language, such as 'signal' and slot', which can be used to denote such methods in a class's declaration. These special modifiers are parsed out by a special-purpose metacompiler, which automatically generates the underlying method-call based code for the signals and slots.

Here's a good page on the topic: http://doc.trolltech.com/3.3/signalsandslots.html

Note that you could use the Qt metacompiler to use signals and slots even without doing anything at all with the Qt toolkit.

Are you really proposing that a program should store two complete copies of all its data? One copy in XML and another as an associative array? I'll note that, in general, it's a very bad idea for a program to try to maintain two distinct copies of the same data. If you're going to keep two copies, you have to make sure they're always synchronized, and that becomes very challenging for anything more than toy examples.

- Warren
 
Last edited by a moderator:
  • #5
Instead of XML you could use dot notation, which encodes the same information and is easier to read. For example, instead of:
Code:
D =
<universe>
<circle ID=10>
<radius>3.0</radius>
<area>unknown</area>
</circle>
<universe>
Send(D, calculator) // now calculator will validate and parse the new information that A wants to know the radius of circle 10, and send back to A some XML stating the area of the circle
this.Get(<universe><circle ID=10><area>areaof10</area></circle></universe>)
Send(areaof10, ScreenOutput)

we would have:
Code:
Calculator = new Object();

D = new Object();
D.Circle = new Object();
D.Circle.ID = 10;
D.Circle.Radius = 3;
D.Circle.Area;

Send(D, Calculator);
AreaOf10 = Get(D.Circle.Area);
Send(AreaOf10, ScreenOutput);

Also, since you're sending D to Calculator, and since Calculator computes the area and places it in D.Circle.Area, then why do you need Get()? I think Get() is implied, for example:
Code:
i = 10;
Print(i);

Implies:
Code:
i = 10;
Print(Get(i));

So we could just use D.Circle.Area instead of Get(D.Circle.Area).
We're not really gaining anything by making this explicit.
 
  • #6
That's a good point, it might be harder to write correct code dealing with XML. But I think that this won't be as much of a problem, for the following reasons:
  1. XML can be validated, so a malformed message can be detected in a standard way, which the programmer would not necessarily have to do himself. In this case that's as simple as checking that everything passed has a table entry for its hash map ID and is of the right type. Most of this could be done at compile time to improve speed, although dynamic type checking is also reasonable (though slightly slower).
  2. XML has standard tools for extracting information from it. I think that using these tools, which could be part of the language, would make programming easier and reduce errors.
  3. I'm basically proposing that the data stored by each object is treated as a tiny database. There are standardized techniques for answering queries in a database, which could also be built into the language. This would also reduce the potential for error.

I am proposing that almost all work that the program does is by using the hash map instead of the raw XML, although writing to a file or reading XML to a file would need to be translated back and forth. It would work like this:
  1. At compile time, all XML data that the programmer put into the code is translated into pairings in the hash table. This is very similar to generating a symbol table, which is a standard compiler step.
  2. All messages passed between objects are pairings in the hash table, with no actual raw XML.
  3. When any text XML is read from an outside source, such as a file or an internet connection, it is all validated and then translated into hash table entries. This is very similar to parsing XML, which is an established process.
  4. When any hash table pairings are written to an outside sink (e.g. a file) they are translated back into XML. I don't know what the name for this is--"un-parsing"?--but any program that parses XML, adds some information to it and writes the XML back, has to do it, so it must also be an established process.
So all the steps that the language would need to take to translate back and forth are all established and well-understood, which reduces the potential for error. They should all be part of the language and not left to the programmer, so once the compiler is properly written it will all work correctly.


Job, you are right. That is another way to do it, which would work perfectly. There are some subtle differences--ways in which I think that XML is slightly better, and ways in which XML is not necessarily as good. First, the ways in which XML does not do everything that dot notation and an object does:
  1. XML does not have efficient arrays and other container types built into it. In the scheme I'm proposing there would only be one container type, a giant hash map. The hash map could act similarly to all the other data types--with some extra machinery (extra machinery that is a standard XML feature) you could treat a list of sub-entries to an entry as elements of an array, and it would not need to be very inefficient as compared to an actual array.

    There is probably a nice way around this. XML is pretty flexible so adding extra container types and the possibility of user-defined containers should be possible. But again, it's not an extremely high priority since a hash map together with the XML nested structure can mimic most common container types without too much loss of performance.
  2. XML is more verbose. This is what I think is the only real trouble with the idea.
  3. Unlike dot notation, I think XML would need a Get function to extract its data, unless you can think of some way that it doesn't have to.

Now, what I think the advantages are:
  1. XML has a standard format that is not tied to any specific programming language. Data that an XML message-passing program produces might be readable by an XML message-passing program that's written in a different dialect. It's like automatic compatibility with every other XML message-passing language (in the event that there ever is more than 1).
  2. The XML data being passed between to objects is human-readable. So is dot-notation if you're using a good debugger, but you could e.g. write some XML to a file and read it with a text editor. This is not a major advantage but I think XML has the edge on human-readability.
  3. Objects contain information about the objects, which could change over time, whereas I would like to have the abstraction that all data represents absolute truth about the universe that is being communicated between two objects. Your typical object would not bother to have an ID of 10, since the other parts of the program can identify it by its memory address. But I think it's important that a message say "The circle with an ID of 10 has a radius of 3" rather than "This circle has a radius of 3." The first is an absolute statement about the universe, which can be determined to be true or false by a human debugger, and the second is not. The human debugger doesn't know which circle is being referred to. This is not really an advantage of XML over objects, because you could also do this with ordinary objects and dot notation if you were disciplined enough. It would still be a different style of programming from usual OOP if you did that though, even in dot notation.
  4. XML has easy ways of specifying its syntax (like DTD). The whole syntax for the entire range of data messages that your program can pass, can probably be specified in a page or so. Dot notation on classes is not as monolithic and is harder to track down. This, I think, is the biggest advantage of XML over dot notation: the ability to specify, in one place, a single language that all of your objects use to communicate.
All in all, dot notation when used properly is very similar to message-passing XML used like I described. There are some differences, and I think using XML tailored to this specific truthful-message-passing framework would be better because of the single DTD or what have you, but "message objects" could also be tailored to a truthful-message-passing framework.
 
  • #7
0rthodontist: out of curiousity, do you have specific goals in mind that you are trying to design it to accomplish?


Incidentally...

But I think it's important that a message say "The circle with an ID of 10 has a radius of 3" rather than "This circle has a radius of 3."
Is there anything wrong with, for example, simply writing toString() to provide that information?
 
Last edited:
  • #8
I think the greatest benefit of an XML-oriented programming language, to make use of its abstraction, would be in translating between languages, as a sort of intermediate dialect. We could, for instance, define a set of standards that the XML PL would follow. Going from XML PL to C, or Java would be straightforward.
Each language, like C and Java, would make available a translator to XML PL, and a translator from XML PL. This would enable us to translate any language to any language.
We already use SOAP for communication between different languages. Each language following the SOAP standards translates the SOAP contents to work with its own framework. The idea would be the same.
Programming with an XML PL directly, IMO, is probably not the best idea.
 
Last edited:
  • #9
Hurkyl said:
0rthodontist: out of curiousity, do you have specific goals in mind that you are trying to design it to accomplish?
It's for the purpose of exploring the object-oriented paradigm and the concept of message passing. It is interesting to me, perhaps not to you.

Do I plan to actually write this language at some point? Maybe. Do I expect this to actually be used in writing some large application? Probably not. I'm not sure I would even like this language very much because it is so verbose about its data.

What advantages do I think the language might have if used on a software project? Easier debugging and an interesting paradigm of "truth based programming" where messages reflect facts about the world rather than commands for an object to do something. This paradigm could aid the development of correct programs because it almost does away with the need for preconditions and postconditions for interactions between objects--so long as the facts being passed between objects are true, objects are behaving correctly. (unless objects aren't getting the facts they need when they need them--which would be a problem with program termination rather than program correctness)

I would actually like to call it "truthful" programming and say that when an object produces only true messages when its input consists of only true messages, that object is "sane."

Incidentally...
0rthodontist said:
But I think it's important that a message say "The circle with an ID of 10 has a radius of 3" rather than "This circle has a radius of 3."
Is there anything wrong with, for example, simply writing toString() to provide that information?
I was talking about the semantic content of the message, not about literally the string "The circle with an ID of 10 has a radius of 3".
 
Last edited:
  • #10
Essentially it IS a logic programming language, where the inference rules are encoded in the Receive() methods of the various objects, and the control of the inference is determined by when various objects happen to send information to other objects. Intra-object actions equal inference, and inter-object messages equal control of inference.
 
  • #11
0rthodontist said:
It's for the purpose of exploring the object-oriented paradigm and the concept of message passing. It is interesting to me, perhaps not to you.
I didn't say it was uninteresting (I am half-computer scientist, you know. :wink:) -- knowing where you want to go with this certainly helps with following the discussion.

e.g. is the "truth-based programming" now a goal that you're aiming for? Or just an interesting possibility?


Are you imagining data actaully being passed directly from one object to another, or there being one or more pools of data, and objects seek and consume the data they so desire?

Yes, it sounds like the former; I'm wondering if you've considered the latter as an alternative. It certainly sounds more interesting, and fits in better with the "knowledge base" idea, methinks: an object could submit request a not-yet computed property of some data, and other objects might inspect the request to see if they can fill in the blank.


"un-parsing"?
I think you want "generate".


I'm not sure I would even like this language very much because it is so verbose about its data.
I sort of feel like you're focusing too much on the trees; you're trying to jump straight into how the language will be implemented, before fully contemplating its high-level design. Maybe a different syntax will suggest itself that isn't so verbose!
 
  • #12
I'm basically proposing that the data stored by each object is treated as a tiny database. There are standardized techniques for answering queries in a database, which could also be built into the language. This would also reduce the potential for error.

Don't structs/records perform that functionality admirably well? Isn't the dot-notation a standard syntax?

Edit: Ah, I see orthodontist has discussed the dot-notation above.
 
Last edited:
  • #13
"Truthful" programming I think captures the concept I'm shooting for here. It's not exactly a "goal" yet, but it's certainly the goal of this hypothetical language.

Yes, I have considered keeping data in a single pool for efficiency reasons. In this case there would be one hash table per program that stores all the XML data that any object has, and Send()ing is simply providing an object with the address of some more data. The "local" data stored by an object would just consist of some hash table indices that reflect which data the object happens to concern itself with at a given time.

A disadvantage of this is that it partially breaks something else I'd like, but don't consider essential, which is that the code inside the objects should be implemented any way and in any language a programmer chooses. Truthful programming + C should be viable, truthful programming + Java should be viable, truthful programming + Lisp should be viable, truthful programming + Prolog should be viable. Once an object receives some XML data (whether actually getting the data or merely being given its ID in the table), it should be able to choose whether it stores the data as actual XML (or hash map ID's) or maybe as an array or as some other data type. If it does change to a different data type, there would be some loss of efficiency but it should still be the programmer's prerogative. The programmer might also use a mix between referring to the XML hash table and his own object-internal representation.

I think that language-independence inside the objects in this case is an important concept, because it is what draws a natural bridge between object-oriented programming and logic programming. An object is a set of inference rules from the statements it consumes to the statements it produces, and the inference rules may be written in any language at all. There might, for example, be heavy use of local classes within these objects, since objects in truthful programming would probably tend to be larger than objects in standard OOP (I'll explain).

In terms of implementation, I am thinking this could be most easily made as a library to an existing object-oriented language. A "truthful" object would be a subclass of Truthful, which would be a class containing Send() and Receive() specifications and the static public XML table they would need, and it would come with XML table/database query lookup/parse/generate/etc. utilities that are specific to objects in truthful programming. The only problem is that I don't know of a nice way to restrict an object so that it can't declare its own methods to communicate with other objects and must use Send(). Maybe it could, at runtime on first startup, use reflection to check for any other public method names and if there are any it throws an error. Also, ideally I would like to prevent the user from talking directly with the screen or internet via language-specific tools--instead they should send truthful messages to screen or internet objects, so that all communication is visible.


The nature of classes in truthful programming would be slightly different from the nature of classes in standard OOP. Their input and output would need to be statements about the world rather than about themselves. For this reason, a generic stack does not cleanly become an object in truthful programming. It would have to make statements like "At system time 0129939, the top element on <stack ID=51/> was <circle ID=10/>." This type of statement would have to be reflected in the single, global specification for the communication between the objects--which is rather cumbersome and doesn't really reflect the "world" state. I conceive the world state primarily to concern the things that the program is designed to deal with, such as IP packets or user interactions, and this is what message passed between objects should concern. An object that needs to pass messages that do not easily translate into those things, I think is more accurately a "data type" than a full object, and should not be represented at the top level, but rather should be dealt with inside the various objects. On the other hand, sometimes a data type will accurately reflect the state of the world--in that case, "The highest priority incoming packet at system time 0129939 was <packet ID=35/>" is a meaningful statement about the world, not just about the stack itself, and a stack that handles such things does deserve a top-level representation as an object.

Objects that produce and consume statements about the real world will typically be end-results of the actions of several smaller data types that perhaps produce and consume mainly commands for each other. For this reason, objects in truthful programming will probably tend to be larger and more abstract than many objects in standard OOP.

Choice of data representation is a troubling issue. XML is somewhat verbose, and more specifically (unless I'm wrong about this) it doesn't allow two different tags with the same name in the same namespace, even if the tags are at different levels of nesting. I think that allowing this would be essential, because you might have entries that want to contain references to other entries. This would mean that it's not quite XML.

On the other hand, there's not much you can do about data verbosity if you want to keep everything human-readable. XML has closing tags as well as opening tags and that's basically the only typing you'll be saving by switching to a different system, at perhaps some cost of legibility. However, data verbosity may not be such a big problem. I think that data, being somewhat simpler than ordinary code, is less difficult to write large amounts of.
 
Last edited:
  • #14
The only problem is that I don't know of a nice way to restrict an object so that it can't declare its own methods to communicate with other objects and must use Send().
If the only way to communicate at the truthful programming layer is through Send() and Receive(), does it really matter if the object declares other things at the underlying java layer?


Actually, the more I think about it, do you really need to say anything about "objects" at all? It seems (to me) the heart of your proposal is that you have a database of "truth", to which XML data may be sent, in which data may be searched, and from which XML data may be removed. Furthermore, there is a contract that any well-behaved interaction with the database cannot decrease its "truthfulness".


Does that resemble your thoughts?
 
  • #15
If it were just a single database of truth, it would be almost indistinguishable from an ordinary logic-programming language. Also, inference would be poorly controlled and it would run the risk of exponential inefficiency (the complexity of purely general, unregulated inference according to a knowledge base). The primary way logic programming gets around that is by sophisticated AI algorithms for deciding what rules are used when, which is completely infeasable if you want to specify your rules in C rather than logic.

Using objects adds control to the language. Each object is only aware of a certain amount of data at a time, reducing its scope, and it is expected to discard some data from what which it is aware of as time goes on. It thereby sidesteps the issue of general logical inference. In addition to that, from a human point of view objects are a good way to structure one's programming, and they allow modularization for large projects.

The objects should be able to declare anything they want, within themselves. But they should be unable to communicate with each other except through truthful statements according to the universe's language specification. It would break the paradigm if objects could communicate with other objects through ordinary method calls; you could have sane objects (objects that generate only truth when given only truth) acting incorrectly because they are given input under-the-table, through method calls.
 
  • #16
I get the feeling you're trying to merge these thoughts about message passing into your thoughts about hiding error-handling code. I get the feeling that you think if pieces of code can be guaranteed to only interact with each other in "truthful" ways, then nothing false can ever be done, and no error-checking need ever be done. You will have finally reached your epitome of code aesthetics, where nothing ever goes wrong by design.

Woe will be the day when a 747 crashes because someone didn't write a library subroutine correctly -- because someone else's specification wasn't absolutely unambiguous -- and it actually spit out some XML that was... false.

- Warren
 
  • #17
Hrm. Before I respond some more, I think I need a sketch of just what "send" and "receive" are supposed to do (in high-level terms). Or maybe a toy application that uses the truth programming facilities -- say, a java program that reads a number from standard input, squares it, and writes the value to standard output.
 
  • #18
chroot said:
Woe will be the day when a 747 crashes because someone didn't write a library subroutine correctly -- because someone else's specification wasn't absolutely unambiguous -- and it actually spit out some XML that was... false.
But that's what it has going for it. It doesn't need preconditions and postconditions--each object can verify independently for itself that it always spits out true XML when it's given true XML, regardless of how grossly misinterpreted its specification is. If each object is sane, which is a property fully local to that object which is therefore easier to verify, then if you misuse them or they send their output to the wrong places at the wrong times, the worst than can happen is you won't get any results at all. It will never produce an actually false result.

Hurkyl, I'll see what I can do but not now. Briefly in high level terms, "Send" sends some XML data to another object, where the data represents a true statement or a few true statements. This may happen either by directly sending the raw text XML (inefficient) or by sending the table references that represent the XML (more efficient) but what it does is send XML data that represents true statements. "Receive" is a method that is never directly called by anything, but is automatically called when an object receives new data. In this way it is similar to an event handler; it handles the event that some other object has Sent the object new facts.
 
Last edited:
  • #19
0rthodontist said:
But that's what it has going for it. It doesn't need preconditions and postconditions--each object can verify independently for itself that it always spits out true XML when it's given true XML, regardless of how grossly misinterpreted its specification is. If each object is sane, then if you misuse them the worst than can happen is you won't get any results at all. It will never produce an actually false result.

How can an object verify that it always produces true XML? What about... bugs?

- Warren
 
  • #20
Yes, it can have bugs, as can all code. The point is that if there are any bugs of correctness, a truthful programming language will localize them to a particular class--so there can be insane objects, and/or nonterminating programs, but if all objects are sane the program is always sane even if it does not terminate.
 
  • #21
You seem to be missing my point... if objects are going to interactively determine the sanity of the other objects with which the cooperate, then there are many, many failure points. Worst of all is the possibility that one object's faulty sanity-detection code will mask another object's bugs -- and then you'll have a buggy system that, collectively, thinks it's "sane."

- Warren
 
  • #22
I'm sorry, perhaps I wasn't clear enough. Objects do not have sanity-detection code. That's the responsibility of the programmer, to ensure all of his objects are individually sane, as part of the larger responsibility of the programmer to ensure that his program is correct. The objects do not interact to determine each others' sanity.
 
Last edited:
  • #23
Oh.. so each programmer is responsible for making sure his own objects are sane? That's equivalent to just saying that every programmer is responsible for making sure his ojects are bug-free, which is not a reasonable thing to demand of anyone.

These blocks are going to have bugs, just like they would in any other language. What's the advantage of all this sanity and truthfulness stuff then?

- Warren
 
  • #24
Making sure that an object is sane is easier than (and different from) making sure the object is perfect. For example, any object that never has any output is always sane, since it never says anything false. It never actually does anything, but in truth-based programming what it actually does can be separated from the question of whether everything that it does is correct (which is what sanity asks). In the calculator example of my first post, the circle would be perfectly correct if it never says anything about the area of circle #10. It would also be correct if it returns a (true) statement that the sky is blue. Neither of these undesirable behaviors would cause the operation of any other objects to actually produce incorrect results--they would simply be unable to proceed, not knowing the area of circle #10.

Back in the standard OOP paradigm, say that I have an object A and an object B, and B has a public method int foo(int x) that has incorrectly written preconditions and postconditions. A programmer writing object A wants to use foo() to calculate the square root of 2. Unbeknowst to the programmer, foo() actually calculates the cube root of its argument. So the programmer will write double sqrt2 = foo(2); and then proceed, and his program will produce the wrong answer. But in truthful programming, the programmer writing object A might say
Code:
D =
<universe>
  <number ID=50>
    <value>2</value>
    <sqrt>?</sqrt>
  </number>
</universe>
Send(D, B)
Get(<universe><number ID=50><sqrt>sqrt2</sqrt></number></universe>)

(note that this is actually much too low-level an operation to be performed at the inter-object level in truthful programming, but for the sake of discussion pretend that A was asking B something important)

Now if B is sane, but still buggy, it might Send() back to A something like
<universe><number ID=50><cubert>1.2599</cubert></number></universe>

A still won't know what the square root of 2 is, but it also won't be misinformed and introduce an error into the calculation. Preconditions and postconditions for inter-object communication are partially replaced by sanity. Instead of a program proceeding to a wrong answer in the face of a faulty specification, it stops, waiting for data, and does not do anything wrong. And someone debugging it, trying to find out what went wrong, will immediately see that object B doesn't know how to compute the sqrt of a number, even if they know nothing a priori about the operation of B.

Is ensuring sanity necessarily easier than ensuring perfect preconditions and postconditions? I think that it would be somewhat easier. Maybe your fellow programmer thinks that you're writing a function that does X, and you thought your function should do Y, which is almost X, but not quite. You just ensure that the object that the function is part of states exactly what new information it provides, and it's instantly visible, as part of the language rather than as part of the documentation, that what your object does and what your fellow programmer thought your object does are not the same. The unified XML language for communication between objects helps you and your fellow programmer communicate specification details.

Primarily, however, it is a device for understanding object oriented programming more deeply and for structuring one's thought about the design of a program. Making a program in the truthful paradigm consists of making a language for all the various relevant things that might be true about the world that your application will deal with, and defining that language in a DTD or something similar, and then making objects that communicate using the language. Whereas in standard OOP you just go straight to the objects and make up the language they communicate with relatively haphazardly, and relatively decentralized.
 
Last edited:
  • #25
This is all well and good for trivial academic exercises like square and cube roots. All you're essentially doing is adding a tag -- a name -- to every piece of data. If your sqrt() function actually returns cubert, then you've detected a bug. Wowwee.

What about the much more common (and much more serious) kinds of bugs, where an object is asked to retrieve some piece of data, and then returns the wrong data?

Imagine that an object represented a class, and the object was asked to retrieve the grade for Warren and Send() it back. It does the work, but contains an off-by-one error, and actually returns the grade for Walter -- but labels it as the grade for Warren.

The receiving object is actually in an even worse state than usual. Now, not only does it have the wrong information, it has evidence (sanity) indicating that it actually has the right information. It might even be more difficult to find this bug, since all the XML is valid, but simply contains the wrong data.

- Warren
 
Last edited:
  • #26
Sanity of an object means that when the object Receive()s only true messages, it Send()s only true messages.

Someone debugging the program would look through the XML that was Sent(), and at one point see an entry like <universe><student ID="Warren30409"><grade>[somegrade]</grade></student></universe> being Sent() out of the grade retriever. He would notice that [somegrade] is not equal to Warren's actual grade, therefore some object in the program is insane. And if he also checked that all previous statements passed to the grade retriever were true--which would be possible because the inter-object language is designed to be human readable--he'd know that the grade retriever is insane, and track down the bug.

Admittedly a bit harder than noticing that the program stops at one point because the needed data is unavailable, but certainly easier than trying to find a bug that could be almost anywhere in the program, in any object.
 
  • #27
0rthodontist said:
Admittedly a bit harder than noticing that the program stops at one point because the needed data is unavailable, but certainly easier than trying to find a bug that could be almost anywhere in the program, in any object.

So... how is that debugging session any different than any other debugging session in any other language? Because the programmer is reading XML? XML rapidly becomes very difficult for humans to accurately read as it grows in size. A large message with hundreds of different tags might be nearly impossible for a human to verify by hand without missing something.

What's the advantage?

- Warren
 
  • #28
It's quite different because what you're reading through are factual statements about the actual world in which the application is supposed to run--instead of having to hunt through the code to figure out what that value x = 7 is supposed to mean.
 
  • #29
It seems like most any bug would eventually manifest itself in a false message, and that's a pretty exciting concept. I don't know how that would necessarily translate into an easier debugging experience, or would promise fewer bugs in the first place.

After all, you might have millions of messages being passed within a program of even modest complexity. If only one out of those million are false, you're never going to find it. If you're lucky, it will corrupt other objects, and you'll get a cascade of false messages and be able to at least tell that something is wrong, even if you can't immediately say where. If you're unlucky, the false messages don't start a cascade.

The debugging problem then turns into a matter of detecting false messages. You could develop some kind of an independent verification arbiter, but that arbiter is going to be essentially just as hard to write as the program itself -- and it will have its own bugs.

I suppose you could have two teams co-develop the program and its verification arbiter, but then you've double your workforce, tripled your cost to market (if you include management expenses), and you might not even wind up with any real product-quality advantage over traditional software engineering practices. (It would have to be studied.)

- Warren
 
  • #30
I think there would not be millions of messages in most such programs. You only need to look at the input to one particular object at a time in order to determine whether the object is sane, which is a tiny fraction of all possible messages. And these are messages at the level of the universe--they are not things like "pop a key from the stack." They are things like "the user Barney logged in at system time 9309480." There would be far fewer of those.

To my knowledge, it was not an existing concept in OOP that messages passed between objects are human-readable, factual statements about the world as opposed to undistinguished data or commands.

In any case, easier debugging is only one aspect of truthful programming. The more important aspect, I believe, is in the design phase where you specify a language of world-level statements in XML (or possibly something else) and then design objects that can talk the language with each other.
 
Last edited:
  • #31
I do see your points, and they are interesting -- I just don't know that they would actually lead to better programs. (Where "better" could mean anything from easier to write, easier to debug, faster, smaller, less prone to errors, etc.)

- Warren
 
  • #32
Don't forget

XY is a programming language; XML is a way to describe data.

I am not in the mood of reading this thread but I think you might be close to this

http://research.sun.com/self/

The Self programming language.
 
Last edited by a moderator:
  • #33
Recently i came across something called XMLVM, used for something called XML11 which reads the Java byte code and places the instructions (elementary ones, such as push/pop ..etC) into an XML file.
There's obviously a lot of overhead involved, but one of its uses is an implementation of the X11 protocol allowing you to have a remote desktop client that runs in your browser completely with Javascript, without the Java plugin.
After converting the byte code to XML, the XML is sent to the browser via AJAX and processed. There's clearly a huge overhead for this, but i saw a demo and it worked.
Basically they made a version of Java's AWT package which interfaces with their XML11 broker, sitting at the server, which then sends the interface to the browser. So you would be able to start any AWT based Java application and see it on a web browser.
This is only slightly related to this thread. :)
 

What is object paradigm?

The object paradigm is a programming concept that focuses on the creation and manipulation of objects, which are self-contained units of code that contain data and methods. This approach allows for modular and reusable code, making it easier to manage and maintain complex programs.

What is message passing in the object paradigm?

Message passing is a fundamental principle of the object paradigm, where objects communicate with each other by sending and receiving messages. This allows for objects to interact and collaborate, making it a powerful tool for creating complex and dynamic systems.

How does message passing differ from traditional programming methods?

In traditional programming methods, data and functions are separate and must be explicitly called upon to interact with each other. In message passing, objects encapsulate both data and functions, and communication between objects is achieved through the sending and receiving of messages.

What are the benefits of using message passing in the object paradigm?

Message passing allows for loose coupling between objects, meaning that changes to one object will not affect other objects. This promotes modularity and flexibility in code, making it easier to maintain and extend. Additionally, message passing supports polymorphism, allowing for different objects to respond to the same message in different ways.

Are there any drawbacks to using message passing in the object paradigm?

One potential drawback of message passing is the potential for performance issues, as objects must constantly send and receive messages to interact with each other. Additionally, message passing can be more complex and difficult to debug compared to traditional programming methods. However, these drawbacks can be mitigated through proper design and implementation.

Similar threads

  • Programming and Computer Science
Replies
7
Views
1K
Replies
13
Views
2K
  • Electrical Engineering
Replies
15
Views
2K
  • Sci-Fi Writing and World Building
Replies
6
Views
637
  • Programming and Computer Science
Replies
9
Views
3K
  • Quantum Physics
Replies
33
Views
2K
Replies
17
Views
816
Replies
9
Views
2K
Replies
1
Views
907
Replies
35
Views
3K
Back
Top