freenode/lisp - IRC Chatlog
Search
16:12:11
phoe
1) because you can't rebind them by accident, 2) because you get all the clos goodness.
16:13:56
jackdaniel
jmercouris: did you consider reading a book about CL? like practical common lisp?
16:14:50
jmercouris
jackdaniel: oh yeah, I totally forgot that chapter about implementation specific details regarding object IDs
16:15:10
jmercouris
jackdaniel: where the author goes into an explanation of why eq would use memory addresses instead
16:15:44
jmercouris
jackdaniel: oh yeah, I also forgot about the section where the author talks about dispatching method performance
16:16:00
jmercouris
where he explains the difference between how long a function call vs a method call takes, and why
16:17:30
Bike
but if you do (xyz 123) you are calling a generic function, which may result in multiple methods being called.
16:18:04
jackdaniel
jmercouris: my point is that you sometimes tend to ask questions that could be easily looked up, like about dispatch macro #:foo
16:21:35
phoe
current CLOS implementations work in a way where GFs must do runtime argument dispatch that cannot be done at compile time
16:21:59
phoe
second, effective methods must be computed - second source of overhead, even if they are cached
16:23:49
phoe
actually lots of this stuff can be precomputed at compile-time; that's what beach is working on now
16:24:19
jmercouris
so you are telling me that SICL will have a really fast generic function dispatch
16:24:28
Bike
what you can't compute ahead of time is the actual dispatch, generally speaking. If you have one method specialized on class xyz, and one specialized on class zyx, and you call the generic function on an argument and it's not discernable at compile time that it's definitely one of those classes, the generic function has to actually check the class.
16:24:31
jmercouris
and that implementation developers will just pop that bad boy into their implementation?
16:25:56
jmercouris
consider this, whenever we create an object, we give it a list of functions it can invoke
16:26:09
phoe
jmercouris: "just pop that bad boy into" is troublesome because different implementations do it differently
16:26:42
Bike
vtables don't always work for lisp because we have multimethods, i.e. a generic function does different things depending on the classes of _multiple_ objects.
16:27:32
phoe
I think this is more or less what already happens e.g. with regard to effective method functions in SBCL
16:27:57
Bike
You could store a map from lists of classes to effective methods in the generic function
16:28:15
Bike
that is pretty much exactly how beach's method works. however, it's still nonzero overhead compared to doing no dispatch at all
16:29:09
Bike
I mean, fundamentally the generic function is doing something the non-generic function isn't
16:29:48
phoe
if you want redefinability at runtime, no, unless you literally want to recompile all of your calling code whenever you add or remove a method I guess
16:29:58
Bike
Usually there's only one or two dereferences to get a function pointer, and then you call that.
16:31:11
Bike
Okay, but I mean, you do whatever lookup at runtime still, since you don't know at compile time that the function is going to be called with objects of classes X and Y.
16:31:49
Bike
If you do know the classes ahead of time you can skip runtime dispatch sometimes kinda, but in general you don't have that information.
16:32:05
Bike
For example you can do like (foo (read) (read)) and then the foo function could be called with literally anything.
16:32:36
Josh_2
I have a large collection of strings and I need to find a string that matches closest to an input string, what datastructure should I use to store my strings?
16:32:55
jmercouris
when I'm doing (salmon x y), it WILL KNOW that salmon is really supposed to be Q (Q X Y)
16:33:44
Bike
I don't think this includes an efficient data structure for lookup though. I don't know what structure would be best off the top of my head.
16:33:59
phoe
jmercouris: yes, that's a special case - if you know argument classes ahead of time then you don't need to check them
16:34:53
Bike
https://github.com/pkhuong/string-case pkhuong wrote this for the case where the match has to be exact, and it's already pretty involved
16:35:44
jmercouris
otherwise we cannot define an efficient data structure, we must know the nature of the data
16:36:01
jmercouris
actually, the compiler could even be intelligent and evolve the data structure over time via usage, or via some parameters
16:36:41
Bike
yeah, it could be pretty involved indeed. pkhuong's thing here doesn't include branch prediction info iirc
16:36:53
Bike
like, if you know that some string is more common than another, you can incorporate that to speed things up a little
16:37:56
jmercouris
Josh_2: I think you will probably want to write your own data structure, nothing built-in will be performant enough
16:38:38
jmercouris
I would write a structure that decomposes the strings into things I can look up via partial parts
16:38:58
Josh_2
for testing purposes the performance isn't a problem, but if I ended up with 10000 different strings and I have to test each user input against them it would end up a problem
16:39:00
jmercouris
I would have a hash table with entries "sal" "salm" and "salmo" all pointing to salmon
16:39:32
jmercouris
Josh_2: if you know some things like length of string you can resaonably decompose the search size
16:41:30
jmercouris
so then you will just make a dict from your source strings, and compare user input to them
16:41:42
beach
jmercouris: The reason most programmers would say that (xyz 123) is a method call is that they know only impoverished languages where a call like that invokes a single method. But Common Lisp has auxiliary methods and also different method combinations, resulting in several methods being invoked by a single call like that.
16:43:22
beach
jmercouris: There is another reason that #:xyz is preferred to :xyz which is that you send a clear message to the person reading your code that only the *name* of the symbol is important, and not its package. Consider a call such as (f '#:xyz 234) vs (f :xyz 234). It is clear that in the first case, only the name of the symbol in important. In the second case, it can very well be a keyword argument.
16:43:54
beach
jmercouris: And it is important to write code so that the person reading the code gets as much information as possible from every element of it.
16:45:26
beach
jmercouris: As many software engineers point out, the compiler is not the only entity reading code. Other tools may as well. So if you use a keyword, the person reading the code might think that some other tool requires a package for the symbol.
16:49:08
Nilby
phoe: flexi-streams can take a byte stream and read it as a character stream, but I don't think it can take a character stream and let you do both read-char and read-byte.
16:52:01
Josh_2
rip seems enchant is broken, trying to (ql:quickload "echant-autoload") it cant find the libenchant.so despite the fact I have installed enchant
16:53:26
phoe
Nilby: hmmm, I don't think that's feasible because of all the different encodings either; inserting a stray byte might break character ordering maybe
16:55:04
phoe
when using encoding X, then the encoded representation of that character is X bits long
16:58:42
Nilby
phoe: It's true it's troublesome. But even normal character streams with encodings have such problems.
16:59:27
beach
Boy, that was a weird discussion on generic dispatch. I guess I am glad I was out right then.
16:59:45
phoe
things are easy when you have UTF-32 and every char is an (unsigned-byte 32) under the hood
17:00:16
phoe
but I guess that what shka_ said is the best way forward - open a byte stream instead of a character one
17:02:37
shka_
it is obviously slower then using builtin implementation facilities for the text streams, but not as significant as i you would think
17:04:46
Nilby
Actually sbcl already does it with it's bivalent streams. I just want it to be portable.
17:06:30
Nilby
Yes. I think I will. It's actually not just interface, it's no having to read the whole thing into memory.
22:22:31
Feldman
So I was looking at Robert Strandh's paper and I wanted to implpment it as my university project. I was told on the discord that you had partial done some of it and that I should contact you.
22:26:23
scymtym
i see. by now, there are multiple implementations that are to some extent based on that technique. what i did is actually pretty far from what the paper describes. part of the reason is that i targeted SBCL
22:26:45
scymtym
i talked a bit about my implementation here: https://techfak.de/~jmoringe/dispatch-demo.ogv
22:28:42
scymtym
as far as i know, SICL (by Robert Standh) has one, ECL has most of the required infrastructure and Clasp more or less implements what is described in the paper
22:30:04
Feldman
Do you think it would still be worthwhile writing my own implementation in the SBCL code?
22:34:08
scymtym
that is worthwhile in my opinion, but i'm not sure it would make a good university project. since SBCL organizes standard instances and also other objects very differently compared to the assumptions of the paper, you would have to bridge over many gaps
22:34:32
scymtym
while that makes the project more interesting and researchy, it is also hard and requires time
22:35:33
Feldman
Officially the project is 300 hours of work, but in practice it ends up being more than that.
22:35:42
scymtym
SBCL has immediate objects with lowtags, instances with a layout, a classoid and a class, "other pointers" with a widetag
22:37:02
scymtym
i think making something that could actually replace the dispatch part of PCL in SBCL is much more work. you could aim for a proof-of-concept, of course
22:38:06
scymtym
you know what, i mentioned that ECL now has some of the infrastructure required for fastgf which was in fact added in order to eventually implement it. maybe as jackdaniel about adding fastgf to ECL instead
22:45:52
Feldman
sorry what do you mean implemented "the thing"? what thing? (infrastructre on ECL, worked on fastgf on Clasp etc)
22:47:28
Bike
i mean, drmeister did it first, but i've pretty much rewritten it all a few times by now, so i'm familiar with the workings
22:50:44
Feldman
My worry with ECL is that if all the "infrastructre" is there, it might not be enough to count, but SBCL does seem much harder yeah.
22:53:11
scymtym
jackdaniel is one of the maintainers of ECL. he should have a good idea of what would need to be done for ECL. he is available in this channel during European daytime most of the time
22:54:04
Feldman
Scymtym, what exactly did you mean by "infrastructure" now that I think of it? I'll make sure to contact jackdaniel as well ofc
22:55:02
scymtym
i don't know any details but i think jackdaniel changed or extended the object representation in ECL to add stamps
1:44:14
npfaro
i have a problem with slime/emacs. When i put the cursor inside a form where the auto-complete would kick in, it puts the Common Lisp one provided from slime in the minibuffer, but then about half a second later it's overwritten by the ELisp one
1:47:21
ludston
npfaro: Are you using the lastest version of Emacs/slime/your lisp implementation? What auto-complete package are you using in emacs?
1:48:40
npfaro
ludston: not really auto-complete but rather the little function signature that appears in the minibuffer. I think it's called eldoc? I just disabled eldoc-mode in the lisp buffer though and it's still doing it so idk
1:55:51
ludston
Probably something in your .emacs file is hooking elisp to the same auto-complete lib? I assume you are coding in both elisp and CL?
2:00:43
ludston
To me it smells like there is some hook in your .emacs file like (add-to-list 'some-elmacs-buffer-hook 'some-elisp-fn-lookup)
2:01:30
Bike
it looks like i have both eldoc and global-eldoc minor modes on but loop displays correctly
2:04:03
npfaro
alright. as far as i can tell, there's nothing touching elisp or slime in my config file
2:11:49
Nilby
I ran into problems like this. But I'm not sure I solved them. I just turned off slime-autodoc.
2:12:07
Nilby
But I have some code like this https://plaster.tymoon.eu/view/2248#2248 in my start up.
2:23:58
charles`
If I want to change directory, load file, then change back, why doesn't this work. It doesn't seem to change directory properly?
2:28:32
Nilby
I'm sorry to say it's complicated and slightly implementation dependent. On some implementations you can just chdir, on some you have to set *default-pathname-defaults*, on some maybe both?
2:48:00
Nilby
Oh, I forgot shcl is the other shell. I use the asdf path for loading, but I guess "cd" and load still works.
3:13:37
npfaro
I'm reading a multi-megabyte file into an array and I think slime is crashing every time it tries to print it
3:40:34
pillton
ACTION has had to wait for the REPL to print out a high-definition image a few times.
3:48:46
npfaro
I have an array of values such that there are groups of 4. so I want to loop over them in groups
3:49:11
npfaro
Say I have #(1 2 3 4 5 6 7 8) I'd like to loop over them so that I can treat them as '((1 2 3 4) (5 6 7 8))
3:49:11
Bike
you mean like you have #(0 1 2 3 4 5 6 7 ...) and you want to work with 0 1 2 3 first, then 4 5 6 7, etc?
3:50:36
Bike
i don't think there's a way to do it with the vector directly. you could cook up something with indices like that.
3:53:17
Bike
i would also do it with the indices. if you want nicer syntax, you could probably design your own clause if you used ITERATE instead of loop
3:53:40
Nilby
or something like (loop with a = #(1 2 3 4 5 6 7 8) for i from 0 below (length a) by 4 do (format t "~s~%" (subseq a i (+ i 4))))
3:57:28
edgar-rft
I think displaced arrays are meant to be used for sub-arrays of big arrays but I need to fiddle out the syntax.
4:03:09
Bike
for large sections the displaced array probably uses less memory than subseq and involves less copying time
4:07:49
Bike
if the chunks are pretty short, i would guess that the copying overhead doesn't matter, and instead you hit slowness because you're using aref on a non simple array
4:07:59
ludston
What is a good word for destructuring a collection into chunks of n length? If it was pairs, you would say "zipping and unzipping"?
4:08:15
Bike
sbcl is probably smart enough to realize that if you're doing aref on subseq it's a simple aref
4:08:44
aeth
However, what I personally do in this situation is use the array macros/functions/etc. that I wrote. https://gitlab.com/zombie-raptor/zr-utils/-/blob/adfe5751a2b327569efb55e0d1c89c7aea9c61f7/array.lisp
4:09:12
aeth
I can decompose an array of length 4 into multiple values, to avoid additional consing (in most circumstances)
4:11:13
aeth
This can compose well with most things, but LOOP doesn't afaik have a way to bind multiple values at once (without a SETF in the body, of course) so it might not be the best kind of iteration for that.