freenode/#lisp - IRC Chatlog
Search
12:25:09
decent-username
I'm about 90% sure ECLIPSE is a bot. If it now starts to talk to me, then that's even more suspicous.
12:36:15
beach
decent-username: Like I said, the convention is to put LOOP keywords at the beginning of a line rather than at the end.
12:38:44
beach
decent-username: Also, page 13 of the LUV slides by Pitman and Norvig has some interesting points. For instance, you should not use a non-Boolean variable in a position that "requires" a Boolean. So when you write (WHEN CELLS ...) you are violating this expectation.
12:40:47
beach
decent-username: And when you write (LET (RESULTS) ...) the message is that RESULTS is "uninitialized" and the person reading your code expects the variable to be assigned to before it is used. But you used it as if it were a list. In that case, you should write (LET ((RESULTS '())) ...)
12:47:14
beach
decent-username: Here is another one: WHEN and UNLESS should be used only in a context where the value is not needed. This expectation is violated when you write (LAMBDA (X) (WHEN (CARVED-P X) X))
12:49:28
beach
decent-username: In a context where the value is needed, use an IF with both branches. So, depending on the message you want to send to the person reading your code, either (LAMBDA (X) (IF (CARVED-P X) X NIL)) [if the value is a default value or a Boolean], (LAMBDA (X) (IF (CARVED-P X) X '())) [if the value is the empty list], or (LAMBDA (X) (IF (CARVED-P X) X 'NIL)) [if the value is the symbol NIL].
12:51:41
beach
decent-username: One more: Instead of writing (setf (cell-features (aref grid x y)) (cons ... (cell-features (aref grid x y)))) it is preferable to write (push ... (cell-features (aref grid y))). In addition, you then avoid multiple evaluations of (aref grid x y).
12:52:37
beach
But, especially, it is much more explicit, since it uses a construct that is the most specific that does the job. That's a general rule in programming. Use the most specific construct that will do the job.
13:00:44
beach
And if you decide to keep the recursive version, a recursive function should always be structured like a proof by induction, i.e. by handling the base case first. So it should read (if (null cells) nil (let* ....))
13:25:43
jeosol
beach: the energy was not wasted at all. There are others that read the code and learn from the style recommendation, how to write better code and design
13:27:27
jeosol
btw, I have a comment above: do you mean (when name ...) should only be used if name is some boolean, or like predicate
13:31:48
beach
This is also why we have two functions NULL and NOT that do the same thing. NOT takes a Boolean argument, whereas NULL takes a list or a default value.
13:33:03
jeosol
You heard about Grahams Bel lisp. What are your thoughts briefly. This is probably discussed here before.
13:34:12
beach
I haven't looked at it. I consider the introduction of new Lisp dialects unnecessary, and I don't understand the reason.
13:34:52
beach
By the way, it doesn't matter much whether we agree or not. Those two people are WAY more experienced than I am, especially when it comes to creating industrial-strength software written by a team of highly experienced professionals.
13:36:00
jeosol
I see, but could that effort not be put in improving the current one, especially if syntax or ideas is close to CL
13:36:56
jeosol
I did ask him a question on twitter a while back, when I started working on my application with CL using CLOS and someone mentioned I will have production issues. I asked him, he said he won't recommend CL at this (that) time but will recommend Clojure.
13:37:45
beach
I might recommend something other than Common Lisp as well, depending on the context. I don't think there is a general-purpose recommendation.
13:39:14
jeosol
which was not bad per see, but I was looking to write a large application, the image-based development probably got me to stick to CL in the initial phase.
13:40:18
beach
A language such as C++ is very hard to use for large applications. At least if you want your application to be both modular and fast. I often say that it is impossible to do that.
13:41:08
beach
The problem is the manual memory management. If your application is truly modular, you can not predict what references to objects might be kept by a particular module.
13:41:27
jeosol
Yes, that was the main issue I was having, layering the classes, organization packages, etc. It was getting difficult so decided to explore something else.
13:42:25
beach
So then, to keep modularity, the C++ programmers either copy everything or they resort to reference counting. Both of which are slow.
13:42:32
jeosol
I saw a CL code for a C/C++ code I wrote. Very concise and the easier to read and was doing more in a few pages that my massive C/C++ code base. The lisp code was for a genetic algorithm some guy wrote for his dissertation.
13:43:31
jeosol
Is there a technical name when a language is few syntax constructs to memorize? Saw something a while ago, but I can't recall
13:44:09
jeosol
I think this is what helps with my coding in CL. I often also have to work in python, pandas, numpy, and the argument keywords, changes here and there. It's hard to keep track and things aren't uniform
13:44:37
jeosol
with CL, I just focus on the application, know how things are structured, not a lot of mental burden.
14:19:14
Josh_2
beach: you wrote all that I am not completely lost xD Is this little snippet of code https://plaster.tymoon.eu/view/1518#1518 wrong? I don't understand
14:50:18
mfiano
I am the author of most of the code that those suggestions were based upon. I never intended the code to be used by others, and my style choices are a little outside the norm to fit my own mental model. Also some of them were for performance considerations. That is why I use Lisp to begin with :)
14:51:37
beach
mfiano: What performance considerations did you have in mind? Are they specific to a particular Common Lisp implementation?
14:53:35
mfiano
Way back when, it was tested on SBCL and CCL. Mostly algorithm and data structure optimizations - I don't think I went as far as to add compiler-specific type annotation optimizations.
14:55:00
mfiano
It's just that I never inteded anyone to use that. I assumed it would stay on my GitHub for me alone, like everything else I write :)
14:55:26
mfiano
The flexibility of the language, both style and not, is why I use Lisp. Otherwise I'd probably have stuck with Python 15 years ago :)
14:56:17
mfiano
The Python philosphy is the language that comes to mind with "only one way to do something"
15:01:25
mfiano
I believe the reason Lisp is so powerful is because of this flexibility. I also believe it's why everyone reinvents the wheel. For most things, it's usually easier to rewrite it yourself to match your own thought processes and use cases, since the original was probably a one-man effort for their specific use-case. After all, code is just a projection of one's own mind.
15:06:33
beach
I read somewhere that understanding code written by others is roughly as hard as writing your own. And that was supposedly not related specifically to Common Lisp.
15:09:17
mfiano
I agree with that. Writing code to be consumed by others is harder than both in my opinion though, even if it has documentation. It's much easier to write code for a particular use-case. Once you start adding users to the mix, edge cases and bugs are found, several refactors and years later, you have a robust piece of software, or a piece of software outside of the original vision.
15:11:00
beach
Indeed. It is harder, but also more rewarding when you find an abstraction that feels right and that can be expressed in the documentation in a useful way.
15:18:52
vsync
beach: interesting, those recommendations, since I deliberately do the opposite for many of them... I may try to reread that chapter to see what the reasoning is. what were the slides you mentioned?
15:21:02
beach
It is all about saving time for unknown people trying to understand your code. So if you don't think you will have unknown people trying to understand your code, of if you don't care about wasting their time, you can write whatever you please.
15:25:52
vsync
yeah, I find that interesting... for example I find (let (foo) bar baz (when foo qux)) more accessible even in foreign code.
15:26:58
vsync
but I value the falseness of empty lists as a feature, not a bug or a dirty programming trick. that's not because it's intrinsically valuable but because it's a part of CL heritage and a key part of CL definition.
15:26:59
beach
So you mean you prefer having absolutely no idea whether foo is going to be assigned to, whether it is an empty list, whether it is a symbol, or whether it is the Boolean false after you see (let (foo) ?
15:27:38
vsync
and, it is obvious to all that a language which allows for shorter programs is strictly superior to one which requires longer.
15:28:41
vsync
;-P --^ I had a page on Everything2 back in the day asserting that car and cdr were superior to first and rests... but the deletionists got to it, in the days before wikipedia
15:30:17
vsync
as for knowing in advance, CL may be the wrong language to demand that in, but you are welcome to use type-declarations; they are the right tool for the job and I often use them myself
15:30:45
beach
So, some great people came up with this convention, and it wasn't me. And many people use it. So when many people use it, it saves time to know that when you see (let (foo), then foo is "uninitialized" and you expect it to be assigned to before being used. If you now don't respect that convention, you will have all those experienced people confused when they read your code.
15:31:36
beach
vsync: So then when they see the variable used, they have to go back and check how it was initialized.
15:32:36
beach
As in two highly experienced developers and software engineers who have worked on industrial projects in teams with many people.
15:32:43
vsync
beach: but some great people also came up with the language, and they did it first, and then people write programs in the language
15:33:29
vsync
btw in that example I selected 2 of the examples together because I would find the whole correct. but it makes complete sense to have something initialized then to check later whether it has been set to anything, or anything has been added to the set that it is
15:35:44
vsync
mfiano: you are conflating notation with semantics; and in the example (let (foo)) one sees neither NIL nor ()
15:36:39
beach
It is interesting to see people who do NOT believe in making life easier for people reading their code.
15:37:07
vsync
beach: you seem to be arguing "these guys used conventions somewhere; therefore everyone should use those conventions everywhere"
15:37:58
beach
Especially when established by highly qualified, highly experienced programmers and software engineers.
15:38:29
beach
vsync: "Conventions" are by definition shared. It is not a "convention" if only you respect it.
15:38:58
vsync
you find this convention persuasive because it matches the way you think. but I don't, because it doesn't match mine.
15:40:40
vsync
first, if one wants to write approachable CL code, one should throw away CL and write the code in Python. because Norvig established the convention that Python is easier to understand.
15:42:15
vsync
rest, the degeneracy of this argument is exposed because Norvig claims Python is closer to his pseudocode... and yet he should therefore use ALGOL which is the official language for pseudocode
15:45:52
vsync
incidentally I was having a casual conversation with my friend who became enraged upon finding out that one would denote keywords by bolding them, and that one could write in a variant which used local language for keywords... I find it a beautiful idea that would be difficult to gain purchase and suspect it never did
15:46:03
mfiano
There's also a difference between confentions that lend to better readability, and conventions that lent to better readability.
15:48:49
mfiano
One example would be the 80 column limit from a time when we didn't have modern displays or operating systems.
15:49:58
vsync
indeed, but in our modern age we no longer have modern displays but instead short-screens; it becomes useful to have short lines in windows one can arrange horizontally
15:59:47
mfiano
It'd be rare to find a document on the web with such a limitation, or even trying to contain a typical URI in a code comment, especially if not at the top-level. Eh, I tile windows horizontally on two of my displays (the 3rd is vertical for long macro-expansions etc), and I don't have a problem even with a 100 column limit and 4 horizontal windows on either of them.
16:10:04
Kabriel
vsync: yeah, doesn't seem all that different than the link I sent. He likes it for communicating his topics, but it was driven by students having issues with CL.
17:15:37
Josh_2
beach: thanks for the suggestions, i changed the intern but as for the defaulting to true, that is only the case with the default values, the function is by another function which provides those values, so It's fine for it to always be true
17:20:44
Josh_2
beach: what about this? https://plaster.tymoon.eu/view/1519#1519 I introduced a new variable and removed the double format
17:37:37
mfiano
It suffers from repeating the same expensive operation more than once, and on multiple ocassions. Before that though, I would focus on proper indentation before asking others to read code
17:39:07
Josh_2
also so what if it is doing reverse a bunch of times, when I have a library I'm happy with I can optimize
17:42:53
mfiano
It's not just reverse. It's also length which is done twice in one branch when it never changes, and is expensive on lists, and subseq conses up a new list twice, likewise for reverse, and more
17:44:31
mfiano
Well only one list consed for subseq, but in combination with reverse is painful to look at for me
17:48:30
Josh_2
okay, I removed repeat calls to length :P but as for the subseq/reverse stuff, I cant' remember what I'm doing so Ima just leave it
17:49:13
Josh_2
also I'm working with lists that are pretty darn short, so all this consing etc isn't expensive
17:56:44
beach
So since LISTP is true for the empty list and the non-empty list, then it is always true, unless the caller passes say 'hello or 234.
17:58:04
Josh_2
and if I don't do the check then a few functions will be passed with that arg and everything will die
17:59:43
beach
You need to read Bertrand Mayer. It is always desirable to signal an error when there is an anomaly. you should never hide it.
17:59:45
Bike
it might indicate that the calling code is doing something you don't expect it to, which you might be interested in knowing.
18:00:19
beach
But I don't think I can handle much more arguing about basic software-engineering ideas tonight.
18:00:58
Bike
if an error is signaled because x is the wrong type, you can find the problem pretty fast.
18:01:22
beach
OK, then I don't think I can handle lengthy justifications of my position on elementary software engineering, with the risk of having those positions questioned, tonight.
18:02:05
beach
Then, yes, always signal an error if there is a chance that the caller might do something wrong.
18:07:24
beach
This technique makes life easier for the person who has to debug defective code, because failure to respect the contract will then not be allowed to propagate more than absolutely necessary.
18:08:59
beach
But I should learn not to get involved in people's personal preferences by quoting elementary software-engineering ideas. The subsequent discussions tend to make me upset, and that's not good for me.
18:20:57
jeosol
beach: again, i know it's good for advise to be received or least pointers in the right direction. You are doing a good service here.
18:23:09
jeosol
I get pointers from the comments you make to others to improve my code. The back-and-forth on some issues can be frustrating. I'll let you run to family now.
19:07:00
Suzuran
We're actually not doing too bad as far as data recovery goes; We're batting above 80% so far.
19:07:57
Suzuran
"Dump completed: Read 803 files having 6659 blocks (23986176 bytes), of which 59 blocks contained data errors."
19:11:37
Suzuran
We had one tape that came back no errors at all, it was really short and didn't have a lispm header; It turned out to be someone's copy of Spacewar for Unix (for old pre-SunOS Suns)