Oo Versus Tables Rants

I am moving the spicier sections of OO-versus-table related topics here to keep the topics nicer. In other words, keep the fighting away from civilian populations.


Moved from AbstractDataType:

[There it is, the dumbest thing you've said yet. We're fucking programmers dude, we like writing hard wired interfaces to behavior, we call them programs. Contrary to what you may think, some tables and some procs aren't a program. SQL is shit, we write programs because we have too, to get what we need. We're not all just out here trying to reinvent databases, databases don't do most of the stuff we need, so we write code that does. We write databases for managing data, and we write programs for behavior. Stacks, are a behavior thing, thus requiring code. Behavior isn't data, and we don't need database to have behavior and exchange and move events and data around. Databases are for persisting data, long term data, databases don't replace variables, hashes, queues, stacks, arrays, etc, you still have to write real code to do anything really interesting.]

There is not much to respond to in that because there is not much specific. The behavior-versus-data issue seems to be a big philosophical divide between us that has never been resolved. I view them as interchangle for the most part, and if they are interchangeable, then one can "shift" a larger portion of their application into data, where it is easier to manage (at least for my head). You seem to think that is some kind of weakness. I don't. If your head happens to work better with code-centric designs, that is fine. Just don't extrapolate that onto others unless you have objective evidence that a code-centric approach is superior.


Moved from AreTablesGeneralPurposeStructures

Top believes that tables can represent all structures and that all other structures are reinventing tables. Please stop arguing with him, he will never be able to see beyond his own opinion. We all know he's wrong, but no discussion with top ever makes any headway. Ignore the trolls please.

Re: We all know he's wrong.

Really? Where is your evidence, my boy? If you have no hard evidence, at least respect my viewpoint.

How about the fact that virtually no-one agrees with you. That's pretty good in my book.

Wiki is biased toward pro-OO because it is sponsored by an OO consultancy. ChrisDate has a pro-table following, I would note. Most WikiZens are also against pure AdVerecundiam. Do you prefer voting as the primary way to determine best technology? Even if I was wrong, it does not hurt to stretch your mind with different ideas.

[Wiki is biased towards OO, because smart people recognize OO's value. OO is pervasive industry wide because it's damn useful in the real world. I prefer common sense the best way to determine best technology, something you don't seem to have. You are wrong, and you should try stretching your mind, as OO'ers minds are far more accepting than yours.]

{I cannot believe somebody actually wrote that. It comes across as gorilla-like chest thumping. If AdVerecundiam and voting are the way to truth, then why not replace most of wiki with surveys? Most shops use OO API's, but generally their created classes are rather procedural in nature. Many OO proponents have made this complaint about production code.}

Any way of representing relations is as expressive as any other.

I am not sure what you mean by "expressive". Is this from a linguistical point of view, or capability? I don't question that a combination of dedicated structures can found to do any specific task that tables can. It is the human engineering and human maintenance issues that make the difference, not can-do-ness. (TuringEquivalency)

If he believes "that all other structures are reinventing tables" then he's obviously wrong because tables were originally proposed as a way of storing data that was, up to then, stored in other ways.

I am not sure I agree with your historical account of tables. Anyhow, if something was used one way 30 years ago and another way later, I don't see that as a problem. OO was originally used for physical modeling, I would note. Finally, I don't think I ever said that other structures reinvent tables. Rather it was "reinvent databases". Databases can be implemented without tables.

I don't believe he thinks that tables are always the best way of representing relations because that is just bad engineering. Any engineer evaluates how the problem domain creates constraints upon the possible solution and then chooses from among the possible solutions for those that resolve those constraints.


moved from ReplaceConditionalWithPolymorphism

[why is this a rant??]

Case statements and similar IF statements "degenerate" better in my observation. If multiple factors come in to play, or if the options grow to no longer be mutually exclusive, the IF statements are easier to change. If you use sub-types, then you have to move code from one class to another upon many changes. I consider moving a more expensive effort than changing code within the same "unit" (function or method). Of course, different domains vary. Domains tied to fixed laws of nature or rigid standards may be stable enough that sub-typing will more likely hold over time. See PolymorphismLimits.

It is sometimes said that repeating case statements are "more duplication". That is not really true. It simply changes the grouping of the duplication so that similar parts are no longer next to each other. Then again, I don't find repeating case statements that often in my code. Each task tends to have case/if lists that are somewhat different, or drift apart over time. I would like to example actual examples you encounter in procedural code. Perhaps there is something else wrong.


Unfair?

I decided to document apparent anti-social or unfair behavior against me or my content for those who claim the problem or evil behavior is always on my side. -- top

The fact that these are your "usual criticisms" is informative. As is your self-perception as a "hated neighbour" Can you see a connection between these two? Or do people hate you for no reason at all?

People jump on you for trolling top, because you can't accept the fact that most people think you are wrong, and you keep inserting arguments every single time anyone mentions OO on any page. We all know you don't like OO, you don't have to keep telling us every time someone mentions OO. There are pages specifically to criticize OO, use them, and don't troll other pages and no one will have a problem with you.

Well, responding to claims is common for those people you "like". I will agree to cut down, but I still think it is unfair. It is voting, not science and logic (although science has aspects of voting to it. But wiki does not really represent the mainstream.) One is allowed to interject if their views are popular, but not if they are not popular.

One is allowed to interject regardless, however you must assume responsibility for what you say, and if you are in the minority, which you are, it's only natural you're going to annoy a lot of people. So while you certainly can interject, you probably shouldn't if your goal is to be accepted by the community and not attacked. While Wiki may not represent the mainstream (I agree with you on that), it certainly represents the cream of the crop among programmers. There are more great programmers here than anywhere else I've seen on the internet. Many times you are arguing with people who are far far better programmers than you are, and you never seem to recognize that, and you never agree with them on anything. It may seem unfair, but wiki represents the consensus (not fairness) of the community, of which you are in a tiny tiny minority, so I'm not sure what you expect.

-- Not every page on OO needs to mention tables/relational, just as not every page on tables/relational needs to mention OO. Please keep this in mind. --


GreenEggsAndHam meets OO skeptics:

  I do not like OO.

Would you try it in the snow?

No, not in the snow, not with a crow. Let me be, you Sam-I-Am. I do not, can not, like OO. Let me be, now please Sam go!

Will you try it with loose types? Will you try it with no hypes? Will you try it without DOM? Will you try it and be calm?

No, I do not want to see OO Watch my mouth, it says "no"!


Is Popularity Evidence?

It's in style because programmers like it, they find it useful, that's what engineering is, practical solutions that practitioners in the field actually use. OO is popular because we like it, if that puts you in the minority, I really don't care, I doubt anyone does. We don't like it for nothing you know, we're not all stupid, we didn't just jump on a bandwagon. You seem to think you have some secret knowledge that you just have to force down our throats about how evil OO is, guess what, you don't. If you like procedural, more power to you, I hope you do well with it, but we don't need you teaching us poor dumb programmers how bad OO really is.

Most developers I know are kind of on-the-fence about OO. And, wiki is biased toward OO because it is hosted by an OO consultancy. I don't dispute that OO works well for you, but I think it is probably a subjective mind-fit thing. Yet, things around here are worded as if OO is a universal objective truth.

It is a universal objective truth, it's not the only truth, but it's one. Look at the new Microsoft.Net framework, OO top to bottom, inside and out, a massive library full of objects. OO is here to stay, you may as well get used to it.

"Here to stay" is a little presumptuous. Microsoft mirrored Java because Java was eating into it's market share, not because of Bill Gates' love of OO. They were adding Perl-like features into VB-Script also when it was in vogue.

Those recordsets you use so much in you're samples, those are objects, those things you use to connect to the database, connections, commands, those are all objects too.

So, they are not much different than the Fortran DB API's I started with, at lease from the API user's perspective. QueryAndLoop

Those widgets you put on forms, labels, textboxes, dropdownlists, datagrids, checkboxes, yup, all objects too. These day's, you can barely write a program without using objects of some kind, even in procedural code, you're usually using some kind of object library to do the work for you.

That is only evidence of their prevalence, not benefits. Besides, using OO API's and writing classes are two different things.

No matter how you cut it, objects are everywhere. OO isn't some fad, it's a reality of the industry. Functional is fast up and coming and may soon challenge OO dominance as more functional concepts make it into mainstream languages, but OO is currently king of the roost in the industry as a whole.

I don't question OO's popularity at the moment, but "packaged" computer software companies make money from change. If something comes along that can out-hype OO, they won't hesitate painting it in Legacy Paint. Built-in (or included) table engines are starting to make a come-back. ColdFusion has them and Microsoft .NET is reported to have them (but I have not verified it yet.)

.Net has DataSets?, DataTables?, DataRows?, and DataRelations?, all objects. Yes, you can do the relational thing in memory with them, though they don't support SQL, but even so, they're still objects. And OO api's are prevalent, because they tend to be easier to use than procedural API's. You may disagree, but the vast majority of the industry disagrees with you, so let's apply OccamsRazor shall we? -- anonymousDonor

How are they easier to use? How is

  action(noun, params)
easier on the API user than:

  noun.action(params)
It is just different ordering of identical elements. Plus some of those API's are bloated IMO. I would rather type and read:

  recordSet['ssn']
than

  recordSet.Fields['ssn'].value
Further, people may be using OO API's that come with the box, but to a large extent they not writing OO classes themselves. If we look at actual uses, the classes many custom application programmers write are generally procedural.

[ Please understand that OO is not just noun-verb-object syntactic sugar. People have been doing OO in C for years, two notable examples being Motif and GNOME. It's even possible to do ObjectOrientedAssembler.

recordSet.Fields['ssn'].value is not OO. Neither is recordSet.getFields().getHash("ssn").getValue(). OO would be recordSet.doSomethingWithSSN(). See LawOfDemeter and http://www.javaworld.com/javaworld/jw-07-1999/jw-07-toolbox.html. You're absolutely right that the classes many custom application programmers write are generally procedural, but that doesn't let you make StrawMan arguments against procedural-in-OO-clothing class libraries. -- JonathanTang]

I am not sure what you mean by the StrawMan statement. Anyhow if you look at what people are actually using and doing with OO and languages, they seem to vote for OO API's into existing "systems" protocols (networking, DB, etc.), but not for managing the business logic itself for the most part. Not that I think votes mean that much, but that is where they point. -- top

You misunderstand me, I'm not saying the records are easier to use because they are OO. They are accessed like so

  aRow["field"]
just as you'd expect using the default indexer on the object. That part was an answer to you saying you thought .NET had a table engine in memory, well, they do of sorts. My point was, even if you had a table engine in memory, it'd likely me made from objects of some sort that you'd use. A recordset is an object But tables and records in memory, in the context of a business problem, aren't object oriented. Tables and Row's are only Object Oriented if you're domain is building databases or database API's. You're arguing against OO seems to overlook the fact that even in procedural code, most programmers use objects, they may not write them, but they use them all the time.

You seem to be saying that "everything is an object", which automatically makes most application OO one way or another.

OO programmers just happen to write their own code in that fashion too. You're right, most people don't do that, I agree that most programmers are procedural programmers. Well, OO programmers simply choose to do their own API's this way too, we like the flexibility of it, we like the freshness of it.

But you can never seem to demonstrate this "flexibility" externally. It is something that makes your brain comfortable, but not something that has any kind of semi-objective metric like less code, less change spots, etc.

I like starting a new project because I get to work with new objects in every project, all tailored to the specific problem at hand. I'd hate coming to work if all I ever used were SQL statements and recordsets, the occasional loop and if statement, I'd be bored to death. A new object's almost like a new toy. A couple simple objects can be used together in a hundred different ways to solve a hundred different problems, they're fun to learn.

OO has better entertainment value? That's a new one.

Procedural programmers like to work with things like procedures, recordset's and structs. An OO programmer thinks that's too low level, we want to work with domain entities. If I build a shopping cart, I want to work with things like Products, Carts, Shoppers, Orders, and LineItems?, not recordsets and procedures.

I work with such "nouns" also, just mostly as tables, not code. You seem to think that tables are less abstract. Well I think they are more abstract because the are generally declarative instead of imperative.

Structs aren't bad, but I don't like having to pass them around.

Some of you keep talking about passing structs or record sets all around. I don't have to do this much if I code well. I don't know why you have this problem with procedural, but it is not an inherent fault of the paradigm, but something else that you are doing wrong or a bad specific language or something.

If I can solidify a concept enough to make a struct out it, I can do better by making an object out if, then I have a place to put all the procedures that use that struct, then I don't have to pass it around to them, and they're all grouped in one place.

Like I keep saying, the relationship between entities and operations are generally many-to-many, not one-to-many. The few exceptions are mostly things that are DatabaseVerbs, which are already implemented for me so that I don't have to repeat them in each class like many OO designs do.

When OO programmers use procedural languages, they tend to use structs with pointers to procedures attached to them. OO is the natural progression of those techniques. You like thinking about your tables as domain entities, because you like to think about the data, you value queryability above all else, so this is a natural reaction. OO programmers don't really care so much about queryability, it's not really important to us in the way it is to you.

It is important to me because it helps me see the information in a more compact or virtually-alterable fashion. I highly value that. I can see patterns that I would not otherwise see in code. It helps be a (pre-insane) John Nash of sorts.

We care about behavior and messages between entities. I don't want to have to write SQL to add an item to a cart, I just want to say aCart.AddItem?(anItem). If you say AddItemToCart?(someItemStruct) procedural style in code, you're implying that there's a cart thing somewhere, so why isn't it's AddItem? function with it?

Okay, in a few cases there might be routines that are one-to-one with entity (I am not sure your example is one, but that is another matter). However, I can group them that way. I can put all entity-X specific stuff in a given file. But, I can put it other ways as needed also. Ideally hierarchical file systems would be replaced with relational databases and I could put all kinds of attributes on routines or modules so that I can see them in any damned order I feel like based on current needs. This gets back to the above query-ability comment.

Code is a different level of abstraction than SQL, they're not really competing. OO code and procedural code also essentially work at different abstraction levels, it's far more than just syntax sugar, it's a different way of thinking about the problem. Procedural id down and dirty, working with programming concepts like recordsets, OO is working at the domain level,

In some ways you are right, but that is because the schema is the big picture, not the code. I neuter the power of code by letting tables be the driver. Together they are no lower an abstraction level than OO.

in terms of the problem entities like Carts, Orders, each containing their functions. We find it makes finding and using and reusing those functions easier than modules did in procedural code. OO techniques were developed from procedural techniques, which you seem to like just fine, so how can you not like OO?

Putting stuff in code makes finding stuff easier than a database that allows ad-hoc querying? I find that veeeerrrry hard to believe.

No, it makes finding code easier, you keep trying to put our behavior into the context of you're data thinking and it won't fit. Database allow querying of data, we don't really believe data should be visible, it's an opposing view. I don't want to see if the item count = 0, I want to see aCart.IsEmpty?, IsEmpty? has context, it has meaning, count = 0 could be a hundred different things, it has no meaning, no context. I don't want to look at the data, I want to ask questions about it, and receive answers to those questions. That's what encapsulation's all about, we don't care about the data, just the answer to the questions, we want the data hidden and not seen, so the object can change the data being used to answer the question any time, it causes no change in the rest of the code. If I need to ask a new question, I write a new method, even if I can get that answer from an existing method, if the new question has a different context. That's what messaging is all about. aCart.Items.Count==0 is vastly different than aCart.IsEmpty? at the conceptual level, the first isn't very OO, the second is, even though both are made from objects. Or consider the Boolean object in Smalltalk. True and False are instances of class Boolean. Both have methods called IfTrue? and IfFalse?, both take blocks as arguments. True executes the block on IfTrue? and does nothing on IfFalse?, False executes the block on IfFalse?, and does nothing on IfTrue?. This is a perfect example of how OO is about polymorphism and messaging allowing flexibility. I never denied that tables were abstract, or said OO was more abstract, just that OO is abstract in a different way. OO has different goals than a table. If you think data is more important than behavior, you'll like tables, if you think behavior is more important that data, you'll like objects. Why you find this so confusing I can't even fathom. -- AnonymousDonor

It is not a matter of "confusion", but a matter of not showing clear benefits.

I could make a function called "isCartEmpty" if need be. However, if it is used only once, then I see no need to wrap something as simple as:

   select count(*) from cart where customerID = $custID
And this is assuming we don't already have the record set in a local variable. If we do, it is even shorter. I generally use YagNi to decide what queries to wrap. But the fact is there that I *can* wrap if needed using functions.

Further, knowing SQL (or a given relational language) one can generally figure out how to see if the cart is empty without finding and inspecting a specific class in the code. It is far easier to scan a schema than classes in code. There are a jillion ways to ask if a cart is empty in OOP:

  cart.isEmpty()
  cart.hasNoItems()
  cart.containsNothing()
  cart.hasZeroItems()
  cart.itemCountEquals(0)
  cart.itemCount == 0
  cart.itemCount() == 0   // wrapped in method
  cart.numberOfThingsInCart == 0
  cart.productCount == 0
  etc...
In this small case it does not matter much. But for more complex stuff, the ways to ask nouns question is more consistent under relational. OO takes many of the DatabaseVerbs and creates DIFFERENT interfaces for each one per shop or developer, leading to less consistency. Less consistency means more time needed to dig around in code to find the "interface".

Relational has in essence factored the interface to common "data things" to one spot, OnceAndOnlyOnce applied to interfaces, not JUST the implementation. OO does a pretty good job of wrapping implementation (but has no monopoly), but nothing for consolidating similar interfaces. Inheritance does not seem to provide the answer, partly because it only applies to specific objects, not collections of objects. Thus, you end up wasting code on things that come out-of-the-box with databases.

As far as your SmallTalk Boolean blocks, it sounds like an interesting example on paper, but how does it translate into better productivity? In functional languages one can execute blocks or closures based on Boolean results also. I don't see why this is an OO specialty. Even so, if you cannot demonstrate how it helps stuff in practice, then it appears to be little more than MentalMasturbation. You like it because it entertains your mind, not necessarily increases productivity. -- top


EditText of this page (last edited September 7, 2005) or FindPage with title or text search