Return Styles: Pseud0ch, Terminal, Valhalla, NES, Geocities, Blue Moon. Entire thread

SICP

Name: Anonymous 2010-04-06 21:31

Say, someone who has no prior experience with programming, and is at a rather 'young' age (Teen still) wants to get ahead of the game, and start up now, rather than later. Would one go about this by reading SICP? I've seen it linked so many times, I've only got to think it's a start.

Name: Anonymous 2010-04-07 17:46

There's so much religion about encapsulation that people tend to forget what the actual point of it is.
Thinking on this, I half agree with you. Pythons approach is equivalent to getters/setters. I was blinded by the case where you do not provide explicit getters/setters.

Going out on a limb, I'd say it's because it's a completely different issue and namespacing doesn't have anything to do with private or public variables one way or the other.
I meant name mangling here . Some people name mangle in C because there aren't namespaces.

Name: Anonymous 2010-04-07 17:56

>>41
Some people name mangle in C because there aren't namespaces.
How the fuck is that supposed to work? I've seen lots of stupid  C code written in the name of encapsulation, but how would name mangling help at all? I'd {love|hate|vomit} to see an example.

Name: Anonymous 2010-04-07 17:57

DAMN (DAMN Against Mangling Names)
***
KEEP OUR SYMBOL NAMES!
PREFER namespace_class_function OVER function_b64HJhn35dA!!!

Name: Anonymous 2010-04-07 18:01

>>42
You know exactly what I meant. SOME_UNIQUE_PREFIX_SOME_FUNCTION rather than SOME_FUNCTION. My terminology was incorrect *hands up*, but I didn't think it would have confused anyone.

Name: Anonymous 2010-04-07 18:03

>>42
also, didn't we have someone who wanted to generate random numbers at compile time a while back. That might work as an example if you generated function prefixes/suffixes instead.

Name: Anonymous 2010-04-07 18:31

>>38
The backtrace myth has already been argued extensively elsewhere and I'm not going to bother repeating it.
Implementing backtrace compression means further complicating all existing interpreters, all tools from debuggers to profilers to code coverage analyzers (for all existing platforms) and so on. To put it bluntly: it's a nice hack that can work for a toy language that simply doesn't have all that ecosystem around. For a real language it's not worth it even if you do it from the very beginning, much less when you are considering such a drastic change after shy of twenty years of evolution.

they preserve proper object oriented abstractions
I have a vague recollection of what you're talking about, I remember deciding that for such a contrived case you are better off implementing your code flow explicitly. I could reconsider if you give me the chance, by providing a link.

Name mangling always was and always will be a hack and relies on you playing nice, which undermines the whole encapsulation point.
No. The point of encapsulation is not in providing security. When you want to run a code that was written by someone who might have not been "playing nice", you need much more than encapsulation to prevent him from formatting your hard drive, and the effort is much better applied at other points and larger scales. Python's name mangling does exactly what it supposed to do with minimal effort, providing a zero chance that someone might not "play nice" accidentally and doing nothing more, not getting in the way of reflection for example.

We complain about it in languages like C which don't have namespaces, why shouldn't we complain about it in python.
I'm sorry, but this makes me think that you don't have an idea of what are you talking about. I hope you are able to find your way to Python reference describing how its name mangling works without my assistance.

Name: Anonymous 2010-04-07 18:37

>>46
Lua's encapsulation is awesome. It's so easy to create sandbox environments.

Name: Anonymous 2010-04-07 18:49

>>44
My terminology was incorrect *hands up*, but I didn't think it would have confused anyone.
You would have confused anyone who knows what ``name mangling'' means. You also would not make a mistake this stupid if you actually understood the concept yourself.

Name: Anonymous 2010-04-07 19:00

>>44
Well no, I didn't. Which is why I asked.

Somehow I had it in my head that this was tied to proper encapsulation rather than just avoiding namespace collisions (that problem is solved without mangling.) I agree though, it's a nasty side of C.

P.S. Calm down!

Name: Anonymous 2010-04-07 19:14

>>46
What about sticking your backtrace into a ring buffer?

>I have a vague recollection of what you're talking about, I remember deciding that for such a contrived case you are better off implementing your code flow explicitly. I could reconsider if you give me the chance, by providing a link.
I was referring to Guy Steele's take on the "Understanding Data Abstraction, Revisited" paper. His example was contrived to fit in a blog post and was about implementing sets in an OO fashion. The example was there to point out that if you do it in an OO manner, then you will build up a large stack because most languages don't optimise tail calls. If you do not optimise them, you have to break the abstraction.
http://projectfortress.sun.com/Projects/Community/blog/ObjectOrientedTailRecursion

Name: Anonymous 2010-04-07 19:20

One thing to take away from this thread:
If you want some discussion on /prog/, insult python.

Name: Anonymous 2010-04-07 20:08

>>50
What about sticking your backtrace into a ring buffer?
And then you write a tail-recursive iteration over some long enough list that crashes at the end, having evicted all useful information from the ring buffer.

Or, you discover that your program blows the heap because some objects that must be long dead are still referenced from your circular buffer. What's more, the behaviour depends on the interpreter settings and isn't under your control.

The root problem is that the idea of TCO that is kind of not always TCO is based on the thoroughly rotten foundation. In fact, the idea of implicit TCO is based on the same rotten foundation as well.

The primary requirement for the core of your programming platform is comprehensibility and predictability. You can have a fuzzy understanding of how exactly some particular library works, but the language itself must be simple, transparent and predictable enough for you to have a fairly accurate mental model of it. Of everything about it, from the parsing (I hope that Perl is not going to die completely and will remain as an example of where the DWIM school of thought leads, for the generations to come) to the memory management. The more important some aspect is, the simpler conceptually it should be, and the more explicit expression it should require whenever the misunderstood intent may lead to a disastrous failure.

TCO itself is deeply flawed in this respect. It is not at all obvious when a call is in the tail position, if you consider more dense coding styles. Can you explain why foldr (+) 0 [1..1000000] stackoverflows? I mean, it doesn't stackoverflow in the foldr itself, stack overflow happens when the expression it constructs is forced, but why is the evaluation not TCO'd?

But it gets much worse when someone tries to invent a stacktrace compression scheme. We had a compiler trying to read the implicit intent of the programmer from his code, but fair enough, at least it more or less depends on the code, if only in an obscure and non-obvious way. Now the algorithm has to read the intent directly from the programmer's mind, because there are no clues whatsoever in the code for whether this or that stackframe is better saved, while some other can safely be discarded!

And it's not something unimportant, some pleasant addition that we can make without, no, when you are in the situation when you see a stacktrace, you are already knee-deep in shit (especially if the stacktrace was mailed to you from an office on the other continent and no, they absolutely can't provide the raw data), and the last thing you want at the moment is to discover that the "clever compiler" did in fact read your mind wrong, performing TCO where you didn't need it at all and discarding the relevant information.

Name: Anonymous 2010-04-07 20:15

TCO itself is deeply flawed in this respect. It is not at all obvious when a call is in the tail position, if you consider more dense coding styles. Can you explain why foldr (+) 0 [1..1000000] stackoverflows? I mean, it doesn't stackoverflow in the foldr itself, stack overflow happens when the expression it constructs is forced, but why is the evaluation not TCO'd?
Foldr isn't tail recursive

Name: Anonymous 2010-04-07 20:17

>>50
http://projectfortress.sun.com/Projects/Community/blog/ObjectOrientedTailRecursion
Yes, that's it.

And it's absolutely hilarious when you actually think about it rather relying on Guy's authority.

As soon as any of his objects is written in a way that does not permit TCO, purely syntactically, like when the dude just wanted to assign the result to a variable and then return the variable, and his abstraction disappears in a puff of decaying unrealistic expectations.

His interface does not encapsulate the thing he relies on, the TCO. His belief that it would be applied through the whole chain goes completely on faith, absolutely not specified for the compiler and not checked for at all.

So I still stick to my original opinion: his example would be better off with an explicit traversal strategy, where it would be immediately obvious that when a set can't just return a value in response to a certain query, then something is wrong, and when the direct implementation for that case would not be TCOed as well, only silently.

Name: Anonymous 2010-04-07 20:20

>>53
Foldr isn't tail recursive
Damn, I meant foldl of course. I think.

Name: Anonymous 2010-04-07 20:23

And then you write a tail-recursive iteration over some long enough list that crashes at the end, having evicted all useful information from the ring buffer.
I did consider that, as far as I can see it isn't really fixable with a fixed size buffer.
Or, you discover that your program blows the heap because some objects that must be long dead are still referenced from your circular buffer. What's more, the behaviour depends on the interpreter settings and isn't under your control.
I thought the circular references were a problem in python anyway because it used reference counting *shrugs*

is not at all obvious when a call is in the tail position
The rules are very plain in functional languages, but I can see it being a problem in imperative ones. It's not uncommmon to see
foo = bar.baz()
return foo

which would ideally be optimized, but that's me digressing into sufficiently smart compiler territory.

And it's not something unimportant, some pleasant addition that we can make without, ...
No-one ever said that you should make do without stack traces, nice strawman

Name: Anonymous 2010-04-07 20:24

>>55
AFAIC it doesn't work in Haskell because they delay all the evaluations, I believe they have a special form foldl' or something that does it.

Name: Anonymous 2010-04-07 20:25

>>55
I mean both variants stackoverflow, for completely different reasons though, but at this point I'd prefer banging my head against the wall to trying to recover or understand anew the useless details of why exactly each of them fails.

Name: Anonymous 2010-04-07 20:28

>>57
Yep, foldl'
http://www.haskell.org/haskellwiki/Foldr_Foldl_Foldl%27

Whatever though, I'm too tired for a flamewar. I concede.

Name: Anonymous 2010-04-07 20:33

>>56
I thought the circular references were a problem in python anyway because it used reference counting *shrugs*
Your moran, circular buffers have nothing to do with circular references, go die in a fire.

Also, CPython uses a generational garbage collector which frees unreferenced subgraphs. You really are speaking out of your ass, my earlier intuition was right.

No-one ever said that you should make do without stack traces, nice strawman
Yours. I stated explicitly that I would not satisfied by the stacktraces that a benevolent moronic stacktrace compressor coded by morons like you would deem worth saving.

Name: Anonymous 2010-04-07 20:37

>>59
Yeah, the question was, in case you forgot it among your nagging...

stack overflow happens when the expression it constructs is forced, but why is the evaluation not TCO'd?

Name: Anonymous 2010-04-07 20:39

>>60
I admit I was ignorant of pythons GC

And no I didn't say that you can make do without a stack trace, I said that it was a myth that TCO and stack traces were incompatible (that is as a rule, not necessarily in a specific case)

If you claim that you don't want/need TCO, fine. For my purposes, I'd rather have it.

You have won. I have nothing more to say, except that it's been a while since I've had such a good conversation in this shithole.

Name: Anonymous 2010-04-07 20:44

>>52
Personally I'm quite happy to have implicit TCO. It's easy to defeat if you really need to.

But you know what? I'm rooting for you. I'm a much bigger fan of pragmatic TCO than merely implicit. Not because I'm the slightest bit worried the wrong call may be eliminated, but because (like in >>54) I would like to communicate to the compiler or interpreter that failing to eliminate a given call is an error--hey it's probably going to crash anyway, but it's much better to know at compile time, or at the very least be guaranteed to know during testing (say TCO fails, but it doesn't exhaust the stack when called with 5, but does with 6. Or with the same values on different machines. Or implementations. Or the phase of the moon.)

That said, I'm still not phased by having my stack trace look ugly. The program has crashed, things are already ugly. And the tools for dealing with ugly cadavers aren't nearly as bad as advertised. So I'm happy to have implicit TCO wherever available, and explicit TCO wherever required, and so on. Ideally pragma should let you set whatever optimizing profile you like.

Name: Anonymous 2010-04-07 20:48

>>61
Prelude Data.List> foldl' (+) 0 [1..1000000]
500000500000
Prelude Data.List> foldl (+) 0 [1..1000000]
*** Exception: stack overflow
Prelude Data.List> foldr (+) 0 [1..1000000]
*** Exception: stack overflow
Prelude Data.List>

The folding itself is TCO'd but the application of
f is still defered.

Name: Anonymous 2010-04-07 20:48

I don't recall the details, but Oz allows you to do some neat tricks with its dataflow variables to make things tail recursive that normally aren't.

Name: Anonymous 2010-04-07 20:53

>>63
I would also be happy with a pragma, it's an interpreter option in Ruby too, no?

Name: Anonymous 2010-04-07 20:55

>>62
I said that it was a myth that TCO and stack traces were incompatible (that is as a rule, not necessarily in a specific case)
No, you have it backwards. TCO and stacktraces are incompatible by definition, because the raison d'etre of TCO is the elimination of some stack frames. Anything that does not eliminate any stack frames is not TCO, but merely a simulation of stack on the heap.

But I would agree that a sufficiently clever stacktrace compressor could eliminate only uninteresting frames most of the time. It's just that "most of the time" is not good enough for me, when applied to such an important thing as stacktraces.

Name: Anonymous 2010-04-07 20:55

>>66
Actually I just checked, it's implementation dependant.

Name: Anonymous 2010-04-07 20:57

>>67
Point taken.
New topic: Should programmers treat the stack like a history?

Name: Anonymous 2010-04-07 21:03

>>64
Yes, yes, I more or less understand what happens there, but it's not at all obvious why the evaluation of the resulting unforced tree of (+)'s is not TCO'd. I mean, it obviously could be optimized in this particular case, right?

More generally, my point was that when you use any external code in a nontrivial way, you can't be sure that it wouldn't blow your stack. The type system doesn't capture the notion of being eligible for TCO through and through.

Name: Anonymous 2010-04-07 21:07

>>67
Pardon me if I'm getting this wrong, but if I phrase my thoughts like that, I realise why you and I have such different views of backtraces. It comes down to a view of the stack as a history versus the stack as a future. Am I wrong?

Name: Anonymous 2010-04-07 21:10

>>70
Well obviously it could be optimised, but it goes against call by need nature of haskell. Although, in a pure function it wouldn't change the answer, it could set of a chain of other previously deferred computations (which may not be needed)

Name: Anonymous 2010-04-07 21:34

>>67
But I would agree that a sufficiently clever stacktrace compressor could eliminate only uninteresting frames most of the time. It's just that "most of the time" is not good enough for me, when applied to such an important thing as stacktraces.
I disagree with this on practical grounds. Finite state machines are, well, finite. And simple recursion doesn't need anything, but maybe you want a counter.

The thing about FSMs is that they simply don't cause any more trace related headaches than iterating would. So any details added by the compressor should be a nice bonus. But I get the feeling you don't write many state machines. (Try not to take that as a judgmental comment.)

What's left? Calls that are neither recursive evaluations nor state machines? In most cases these are relatively shallow, and obviously so. I will admit to having written what I consider to be excellent code that violates that rule, but while I didn't set out to write a state machine I'm not sure it is undeserving of being so classified. What am I saying here? - I think it is reasonable to expect a selective kind of optimization that can deduce with great accuracy whether or not a call should be optimized, on the grounds that state machines and recursion should optimize (and maybe things you'd normally inline), and that's it.

>>69
It's a pedantic point, but I think those who do in an absolute sense are fools. OTOH I can forgive those who aspire do so for practical purposes even if I can't identify with them.

Name: Anonymous 2010-04-07 21:55

is there any reason you cant have both TCO and stacktraces at the same time that i am missing?
as my mspaint art shows
http://img30.imageshack.us/img30/1497/tcostacktraceincompatib.png
it should work out fine in theory

Name: Anonymous 2010-04-07 22:05

>>74
As I kept saying it's fine and does work, for example PLT gives you some nice pretty arrows pointing about your code. Various other schemes have tracing libs.

Name: Anonymous 2010-04-07 22:08

>>74
Hint: try that on something that isn't simple recursion, Randall1.

--
1. he would know better.

Name: Anonymous 2010-04-08 0:06

Just wanted to point this out to everyone posting about Lua: Lua is not a programming language. It is a scripting language. i.e. if you lua script, then you're a skiddie.

Name: Anonymous 2010-04-08 0:58

>>77
Insight: 1/10
Humour: 3/10
Trolling: 9/10

Get the fuck out.

Name: Anonymous 2010-04-08 2:00

HAY!!! GUISE! I JUST CAME BACK FROM SMALLTALK AND
ENSCAPULATION
IS
EXPLICIT

Name: Anonymous 2010-04-08 7:48

>>79
Explicit_Hardcore_Double_Encapsulation.dvix

Newer Posts
Don't change these.
Name: Email:
Entire Thread Thread List