I did some research this weekend about OOP. I more or less took it for granted that OOP is what it is and didn't think much about it until just recently. Nothing new, but some links that I found interesting. I plan to add more when (if) I find them.
Paul Graham (the world's only celebrity Lisper)
Why Arc Isn't Especially Object-Oriented
The Hundred-Year Language
Joe Armstrong (creator of Erlang)
Ralph Johnson, Joe Armstrong on the State of OOP
Why OO Sucks
Jeff Atwood
Your Code: OOP or POO?
Karsten Wagner
OOP is Dead
Alan Kay (who coined the term)
Dr. Alan Kay on the Meaning of “Object-Oriented Programming”
prototypes vs classes was: Re: Sun's HotSpot
Generic programming vs object oriented programming
Type erasure
Object Orientation is a Hoax
Richard Gabriel and Guy Steele
Objects have failed
Objects have not failed
Other
Problems With Existing Oop Evidence
OOP Criticism
SICP (the course, not the book)
OOP in Scheme
OOP vs type classes
Haskell vs OOP
A fresh look at OOP with concurrent objects
Teaching FP to Freshmen (The comments are informative, as it's clear the OOP supporters are not willing to defend Java/C++-style OOP. Yet for all practical purposes Java/C++-style OOP is OOP.)
Bjarne Stroustrup keynote at GoingNative 2012 I can't find the quote right now, but Stroustrup makes it clear that C++ is much more than an OOP language. He says something along the lines of, "inheritance can sometimes be useful".
Stop Writing Classes
HN Discussion of Stop Writing Classes
Of course, there are alternatives to what is usually called OOP. As I've learned, it's tough to even get a definition of OOP.
Rifle-Oriented Programming with Clojure
I'm not anti-OOP. I just think there are better ways to do what is done in C++ or Java.
Observations, solutions to problems, and even a few rants about Linux, free software, and computing in general
Monday, October 31, 2011
Friday, October 28, 2011
Restarting sound on Debian Squeeze
Finally found something that works. Many thanks to the author of this post.
sudo /etc/init.d/alsa-utils stop
sudo alsa force-reload
sudo /etc/init.d/alsa-utils start
sudo /etc/init.d/alsa-utils stop
sudo alsa force-reload
sudo /etc/init.d/alsa-utils start
Clojure and OOP, part II
I gave some thoughts about Clojure and OOP last week. Now that I've got a little spare time, I want to finish those thoughts.
First, I want to link to this post by Stuart Halloway. It was one of the first posts I read on Clojure (and potentially the first time I had heard of Clojure). Without it I may not have even bothered with Clojure. I'm not a big fan of OOP, and don't use it that much, but I didn't think I could completely give it up.
Encapsulation
I didn't address the issue of encapsulation at all in my previous post. That's because, to me, encapsulation has never been a big issue.* In C++, you declare the inner workings of your classes to be public, private, friends and probably some others that I don't know. It's similar to running a web service. You can't open everything to anyone who wants it.
To be honest, I've never been in a situation where it would have been worth the work to set up an elaborate system in which I define who gets access to what. If there is a piece of data that should be accessible to the outside world, why can't I just use getters and setters? If there's no "get" defined, then I shouldn't be accessing the data.
Maybe to better summarize my experience, I'm not disagreeing with the concept of restricting access to data. What I don't see is how declaring public, private, friends, and whatever, and all the complexity it adds, plus all the work it creates (you have to do it for every class) is better than getter and setter functions combined with common sense and a few simple rules. The C++ approach seems no more reasonable than Haskell's purity requirement. Trying to debug a complicated OOP program is no fun. Maybe I work on smaller projects and don't have ten million lines of code and a hundred programmers of varying quality working with me, so my observations don't carry over to those situations.
For what it's worth, here is Rich Hickey's answer to an interview question by Fogus: "Following that idea—some people are surprised by the fact that Clojure does not engage in data-hiding encapsulation on its types. Why did you decide to forgo data-hiding?"
(Warning: partial quote) "...And if you have a notion of “private”, you need corresponding notions of privilege and trust. And that adds a whole ton of complexity and little value, creates rigidity in a system, and often forces things to live in places they shouldn’t.... If people don’t have the sensibilities to desire to program to abstractions and to be wary of marrying implementation details, then they are never going to be good programmers."
I see nothing controversial about that perspective.
Clojure and Learning OOP
I included the word "learning" in the title of my earlier post. I would argue that Clojure is a much easier way to learn about the underlying concepts of objects (but using maps), polymorphism, and inheritance. These are concepts that every programmer should understand and use.
I would go further, though. Even if you want to use OOP in Java or C++, you're better off to start with Clojure. The advantage of Clojure over Java/C++ is that you can learn one thing at a time. It's very easy for anyone to understand what's going on when you introduce a single concept. With Clojure, the concepts are well-motivated.
In Java or C++ you get hit with everything at one time. There's a lot of coupling. The degree of difficulty rises very quickly with lines of code when someone is trying to learn something. Introducing the grouping of related data, methods, and the system of privileges all at once is not only too difficult, there's no motivation. I've been programming for decades, and I don't see a need for C++-style encapsulation. How is a new programmer supposed to understand?
Only then do you get into polymorphism and inheritance, concepts they have a reason to learn. Give me an hour with a new programmer and I'll have him doing polymorphism and inheritance, and he'll have at least a small understanding of what they are and why he'd want to use them. Then put him in a class on Java or C++ and he'll have no problems. That's why you're better off to start with Clojure even if the goal is to train them in a more "practical" language.
Parenthesis Whining
As an aside, for those who think the use of parenthesis makes Lisp unsuitable for teaching programming, let me present you with Hello World! in Java:
In Clojure, Hello World! is
One set of parenthesis vs two in the Java program. Plus the Java version has two sets of {}, class, public, static, void, System.out, and String[]. If that doesn't make a programming newbie vomit, nothing will.
As with my other post, I'll conclude by admitting I'm not an OOP expert. I appreciate any comments you might have.
* If it were, I would have to stop programming in R, because I'm not aware that R offers real encapsulation.
First, I want to link to this post by Stuart Halloway. It was one of the first posts I read on Clojure (and potentially the first time I had heard of Clojure). Without it I may not have even bothered with Clojure. I'm not a big fan of OOP, and don't use it that much, but I didn't think I could completely give it up.
Encapsulation
I didn't address the issue of encapsulation at all in my previous post. That's because, to me, encapsulation has never been a big issue.* In C++, you declare the inner workings of your classes to be public, private, friends and probably some others that I don't know. It's similar to running a web service. You can't open everything to anyone who wants it.
To be honest, I've never been in a situation where it would have been worth the work to set up an elaborate system in which I define who gets access to what. If there is a piece of data that should be accessible to the outside world, why can't I just use getters and setters? If there's no "get" defined, then I shouldn't be accessing the data.
Maybe to better summarize my experience, I'm not disagreeing with the concept of restricting access to data. What I don't see is how declaring public, private, friends, and whatever, and all the complexity it adds, plus all the work it creates (you have to do it for every class) is better than getter and setter functions combined with common sense and a few simple rules. The C++ approach seems no more reasonable than Haskell's purity requirement. Trying to debug a complicated OOP program is no fun. Maybe I work on smaller projects and don't have ten million lines of code and a hundred programmers of varying quality working with me, so my observations don't carry over to those situations.
For what it's worth, here is Rich Hickey's answer to an interview question by Fogus: "Following that idea—some people are surprised by the fact that Clojure does not engage in data-hiding encapsulation on its types. Why did you decide to forgo data-hiding?"
(Warning: partial quote) "...And if you have a notion of “private”, you need corresponding notions of privilege and trust. And that adds a whole ton of complexity and little value, creates rigidity in a system, and often forces things to live in places they shouldn’t.... If people don’t have the sensibilities to desire to program to abstractions and to be wary of marrying implementation details, then they are never going to be good programmers."
I see nothing controversial about that perspective.
Clojure and Learning OOP
I included the word "learning" in the title of my earlier post. I would argue that Clojure is a much easier way to learn about the underlying concepts of objects (but using maps), polymorphism, and inheritance. These are concepts that every programmer should understand and use.
I would go further, though. Even if you want to use OOP in Java or C++, you're better off to start with Clojure. The advantage of Clojure over Java/C++ is that you can learn one thing at a time. It's very easy for anyone to understand what's going on when you introduce a single concept. With Clojure, the concepts are well-motivated.
In Java or C++ you get hit with everything at one time. There's a lot of coupling. The degree of difficulty rises very quickly with lines of code when someone is trying to learn something. Introducing the grouping of related data, methods, and the system of privileges all at once is not only too difficult, there's no motivation. I've been programming for decades, and I don't see a need for C++-style encapsulation. How is a new programmer supposed to understand?
Only then do you get into polymorphism and inheritance, concepts they have a reason to learn. Give me an hour with a new programmer and I'll have him doing polymorphism and inheritance, and he'll have at least a small understanding of what they are and why he'd want to use them. Then put him in a class on Java or C++ and he'll have no problems. That's why you're better off to start with Clojure even if the goal is to train them in a more "practical" language.
Parenthesis Whining
As an aside, for those who think the use of parenthesis makes Lisp unsuitable for teaching programming, let me present you with Hello World! in Java:
class HelloWorldApp { public static void main(String[] args) { System.out.println("Hello World!"); } }
In Clojure, Hello World! is
(println "Hello World!")
One set of parenthesis vs two in the Java program. Plus the Java version has two sets of {}, class, public, static, void, System.out, and String[]. If that doesn't make a programming newbie vomit, nothing will.
As with my other post, I'll conclude by admitting I'm not an OOP expert. I appreciate any comments you might have.
* If it were, I would have to stop programming in R, because I'm not aware that R offers real encapsulation.
Friday, October 21, 2011
Clojure, a great way to learn OOP
Edit: There are two parts to this post. You can read the second part here.
Clojure is not sold as an OOP language, but it is a great way to learn OOP concepts. I had the (mis)fortune of learning OOP by using C++. I actually tried to learn OOP with Java and Python, but the problem was that the examples were so completely pointless that I was able to learn how to do OOP in those languages, but I never learned what OOP actually is. I had to learn that while using C++ to do things that made sense.
I will admit that I'm not a big fan of OOP. I always read that it reduces complexity, that it makes it easier to model your problem, but in most cases I didn't see that the benefits outweighed the overhead.
I've learned something while using Clojure. Nobody really cares about OOP. We care about what OOP does for us, and you can get the benefits of OOP without the BS of C++/Java-style OOP. Objects and polymorphism are convenient. Clojure has made me realize that there are alternative (and IMO far better) ways to get the benefits of OOP.
Here's a quote from Practical Clojure by Luke VanderHart and Stuart Sierra (which I highly recommend if you have no knowledge of Clojure): "The most important example is that maps can do 90 percent of what objects do in an object-oriented program. What real difference is there between named properties of an object and a key/value pair in a map? As languages like Javascript (where objects are implemented as maps) demonstrate, very little." It was nice to see in print something that I've been realizing for myself.
Maps and multimethods are not only very easy to understand, it's tough to learn them without also knowing why you'd want to use them. There's so much formal BS with C++/Java OOP that someone new to the language can't really capture everything. With Clojure you do a lot less and get the same benefits. It's also a natural part of programming in Clojure, even if your program is only 40 lines long, which means it's perfect for introductory programming classes. OOP is sold in the C++/Java world as a way to handle large-scale programs. There's no reason for that to be the case.
It seems strange to say it, but using Clojure has pushed me in the direction of OOP.
{I am not claiming to be an expert in OOP. Take my comments as coming from someone who is a little bit more than a beginner when it comes to OOP. I'd love to hear your thoughts if you disagree. I might learn something.}
Clojure is not sold as an OOP language, but it is a great way to learn OOP concepts. I had the (mis)fortune of learning OOP by using C++. I actually tried to learn OOP with Java and Python, but the problem was that the examples were so completely pointless that I was able to learn how to do OOP in those languages, but I never learned what OOP actually is. I had to learn that while using C++ to do things that made sense.
I will admit that I'm not a big fan of OOP. I always read that it reduces complexity, that it makes it easier to model your problem, but in most cases I didn't see that the benefits outweighed the overhead.
I've learned something while using Clojure. Nobody really cares about OOP. We care about what OOP does for us, and you can get the benefits of OOP without the BS of C++/Java-style OOP. Objects and polymorphism are convenient. Clojure has made me realize that there are alternative (and IMO far better) ways to get the benefits of OOP.
Here's a quote from Practical Clojure by Luke VanderHart and Stuart Sierra (which I highly recommend if you have no knowledge of Clojure): "The most important example is that maps can do 90 percent of what objects do in an object-oriented program. What real difference is there between named properties of an object and a key/value pair in a map? As languages like Javascript (where objects are implemented as maps) demonstrate, very little." It was nice to see in print something that I've been realizing for myself.
Maps and multimethods are not only very easy to understand, it's tough to learn them without also knowing why you'd want to use them. There's so much formal BS with C++/Java OOP that someone new to the language can't really capture everything. With Clojure you do a lot less and get the same benefits. It's also a natural part of programming in Clojure, even if your program is only 40 lines long, which means it's perfect for introductory programming classes. OOP is sold in the C++/Java world as a way to handle large-scale programs. There's no reason for that to be the case.
It seems strange to say it, but using Clojure has pushed me in the direction of OOP.
{I am not claiming to be an expert in OOP. Take my comments as coming from someone who is a little bit more than a beginner when it comes to OOP. I'd love to hear your thoughts if you disagree. I might learn something.}
Monday, October 17, 2011
Installing a Network Printer on Scientific Linux 6.1
Took me a while to figure this out. Can't use the http://localhost:631 configuration window. Have to go to > System > Administration > Printing. Click on New. Click on Find Network Printer. Enter the IP address in the text box next to "Host...". Click on Find. The rest should be straightforward.
I had to find the IP address by printing the network configuration page from my HP wireless printer.
I had to find the IP address by printing the network configuration page from my HP wireless printer.
Friday, October 07, 2011
Adding existing Clojure files to a project in Counterclockwise
I haven't done this in a while, and it took me a while to find out how to do it again. {Insert rant about how things get done in the Java world.}
Under the project name, right-click on "src". Click on Import.... Under "General" click on "File System". Click next.
Click on the Browse... button and select the directory (has to be different from the current project directory). Check the boxes beside the names of the files you want to add.
Not exactly the most intuitive procedure, but par for the course in the Java world.
Under the project name, right-click on "src". Click on Import.... Under "General" click on "File System". Click next.
Click on the Browse... button and select the directory (has to be different from the current project directory). Check the boxes beside the names of the files you want to add.
Not exactly the most intuitive procedure, but par for the course in the Java world.