Modify Lisp function without rewriting it? - lisp

I wrote a Lisp function earlier that had an error. The first challenge was to figure out how to view the function again. That challenge is solved. Now that I see WHAT I have done wrong, I want to modify the contents of the defined function without rewriting the whole thing?
Seems like as intelligent as Lisp is, there HAS to be a way to do this, I just don't know what it is because I am fairly new to the language. Can this be done?

Judging from the question, I think that you have a strange setup. It seems to indicate that you are writing your functions directly at the REPL. Don't do that.
The usual setup is to have an IDE (for example, Emacs with Slime) where you edit a source file, and then "send" top-level forms (like function definitions) to the REPL.

Every useful REPL has a history functionality. It allows you to move in the history of your input backwards and forwards.
When I write code in the REPL simple keystrokes like m-p gets back earlier code. Some IDEs might even be able to locate source code in a Lisp listener with m-. .
In most REPLS you can also search incrementally backwards.
If you want a log of your input use the function DRIBBLE..
There are some more options, like retrieving the code from the function - when a Lisp IDE supports that.

There is the advice functionality in many Lisps, which lets you run additional code before or after or around an existing function. But the comment is right, why wouldn't you rewrite a function if you're still learning and trying things out? Do they charge you by the compile cycle?

Related

Portacle Lisp : Slime-repl-sbcl prompt keep auto-scrolling back

as the title said, I am learning common lisp right now and using portacle, following Practical Common Lisp by Peter Seibel.
I found it quite annoying that the Slime-repl-sbcl buffer keep the writing at the end of the screen (using C-l or C-v doesn't help since once I try to execute an expression it will roll back to the end of the screen)
Is there anywhere to improve this? (should I just write on a text file and compile it? the only similar subject I found was about Cider repl and couldn't understand it, since I am still new to lisp)
Thank you for your time
I would like this fixed too. No solution yet. In slime-repl.el, I found:
scroll-conservatively (variable):
A value of zero means always recenter point if it moves off screen.
my test wasn't conclusive.
slime-display-output-buffer (function), which calls slime-repl-show-maximum-output, which role is to
Put the end of the buffer at the bottom of the window.
I rewrote slime-display-output-buffer without this call, but that wasn't conclusive either.
Maybe I tested badly.
(I'm making this answer a wiki)
You would indeed typically write in a source file, and compile each expression separately. Use the REPL only to test functions or do simple computations. To compile functions (or really, any toplevel expression), use C-c C-c - bound to slime-compile-defun by default - when the point (= your cursor) is inside the function's code. The REPL will then "know" of it, so you can test it there, but as it is now written in file, you can also modify it without having to copy/paste anything ! Just make sure to recompile functions that you modify !
If you want to compile/load entire files at once, look at the other compilation commands, e.g. slime-compile-and-load-file (see the SLIME manual, and its Compilation section)
For your problem: there is Emacs variable, named comint-scroll-to-bottom-on-input (or something along those lines, can't remember exactly ...) which enables the behaviour you are seeing, so that you don't have to scroll back to enter new expressions. It is possible that SLIME has another variable which configuring this behaviour for its REPL; in that case, it would probably be named almost the same, and you can set it to nil to disable it.
Finally, don't hesitate to look at the other tools provided by SLIME ! For example, it comes with an "inspector" (see the relevant section), that you can use instead of evaluating expressions such as *db* in the REPL. In that simple case, it makes no real difference, but if you start having - say - hash-tables or different structures/classes, it becomes an incredible tool for interactive development, to examine the internal of almost everything, redefine things directly from within the inspector without needing complex accessors, and so on.

defadvice in emacs, what's correct context to use it

Could someone please have a brief explanation on (defadvice ...), I'm not getting when is the suitable context to use it, seems it's not common in C/C++/Java languages? Such as the example shown in the figure attached. Many thanks.
Advising a function (whether using defadvice or the more recent advice-add etc.) is an alternative to redefining it.
If you are not the author of a function, and if it might already be used in various places beyond your code, you can either redefine it or advise it, and thereafter each use of that function will use your redefinition or your advice. And this is reversible: you can disable your advice.
Redefining a function does not, in general, play well with other libraries, which themselves might want to redefine or extend it in some way.
The point of advice is that it allows multiple libraries to alter or enhance a function definition in a reasonably controlled way, so that there is less chance of the different libraries stepping on each others' toes. Or at least so that it is easy to remove the effect of any of the library changes to the function.

Is there a quick way to show the code of a method declared in the Scala Console?

I frequently use the Scala console to evaluate and test code before I actually write it down in my project. If I want to know the contents of a variable, I can just enter it and scala evaluates it. But is there also a way to show the code of methods I entered?
I know there's the UP-key to show single lines, but what I was searching for is to show the whole code at once.
There's a file in your home directory named .scala_history that contains all of your recent REPL history. I regularly copy and paste code from this file into project source files. It's not exactly the same as showing the code for individual methods in the REPL, but it might help you accomplish the same goals.
See the comments by Paul Phillips in this issue for a discussion of some related functionality in the REPL (grouping statements in the history):
At some point I implemented the logic for this, but the real obstacle
is jline. It has enough trouble figuring out where the cursor is under
the simplest conditions. Start throwing big multiline blocks into the
history and it breaks down in tears. Would love to see this and
SI-2547 addressed by the community.
...
I expect to fix this soon too, but it depends on how well the recent
jline work goes. I implemented it long ago, and display issues are the
impediment.
Both of these comments are over two years old, so I wouldn't hold your breath.
I dont know a command to load all the code from command line.
What you can do is to :load path/to/my/file.scala to load some complex code and re- :load it when you changed the code in the file.

Learning Common Lisp tips for a Windows/C++ programmer

I'm an experienced C++/.NET/Java Windows/web programmer trying to learn (Common) Lisp. I'm reading Practical Common Lisp and using SLIME.
I'm getting the Lisp language easily enough, but I'm having trouble groking the mechanics of development. One of my issues is dealing with Emacs. I have no experience with it and find it generally confusing with hard to find/figure out commands.
Specific questions:
I get the REPL, but I don't quite get how I can use it effectively. When I need to change a function I have to retype the defun and make changes (tedious and error prone). How can I do this better?
How do I get from entering code at the REPL to actually having a program? I'm used to the C model where you have code files that you can review, edit and recompile. I know Lisp has something similar (via the load function), but how does one get a function I just defined and tested into a file to be saved? I'm hoping there's a better method than my current select+copy+paste.
How do you debug errors? Is there any ability to step into code like I would with other languages?
As long as the S-expression is valid, I don't get any errors when entering a (defun ...). It's not until I try to use it that I find out it's not valid. Is there any way to get errors sooner (i.e. compile the code)?
Is there some IDE that would be more familiar to me or allow me to play with the language easier?
Should I switch to learning Scheme instead?
Any tips would be greatly appreciated!
-I get the REPL, but don't quite get how I can use it effectively. When I
need to change a function I have to
retype the defun and make changes
(tedious and error prone). How can I
do this better?
-How do I get from entering code at the REPL to actually having a program?
I'm used to the C model where you have
code files that you can review, edit
and recompile. I know lisp has
something similar (via the load
function), but how does one get a
function I just defined and tested
into a file to be saved? I'm hoping
there's a better method than my
current select+copy+paste.
Load SLIME. Enter code in your .lisp file, and then run slime-eval-buffer to load all your code into Lisp. Then, for a specific function you are hacking on C-e, C-j to redefine it in your running Lisp.
-How do you debug errors? Is there any ability to step into code like I would with other languages?
Yes. (trace 'my-function) - or some variant on that - and when my-function is called, it will break into the debugger.
-As long as the S-expression is valid, I don't get any errors when entering a
(defun ...). It's not until I try to
use it that I find out it's not valid.
Is there any way to get errors sooner
(i.e. compile the code)?
To some degree, that is a characteristic of dynamic languages (Python, Perl, Ruby, Lisp, etc.). Try SBCL for better error-checking.
-Is there some IDE that would be more familiar to me or allow me to play with the language easier?
Emacs is the free IDE for Lisp. Allegro has a free edition I believe; I've never tried it though..
-Should I switch to learning Scheme instead?
Nah, Scheme is not as pragmatic a language.
I'm an experienced C++/.NET/Java Windows/Web programmer trying to learn (Common) Lisp. I'm reading Practical Common Lisp and using SLIME.
One can also use the LispWorks Personal Edition for learning Lisp. It has some limitations and the full product is commercial, but it is quite a bit easier to use.
I get the REPL, but don't quite get how I can use it effectively. When I need to change a function I have to retype the defun and make changes (tedious and error prone). How can I do this better?
The REPL has a history. With keyboard commands you can get back prior input and change it. Other than that just edit a Lisp file and compile code from there. In Lisp you can compile/eval individual expressions and definitions. Typical IDEs like SLIME, LispWorks or Allegro CL allow you to run code also from normal Lisp text windows - additionally to executing expressions in the REPLA (aka Listener).
How do I get from entering code at the REPL to actually having a program? I'm used to the C model where you have code files that you can review, edit and recompile. I know Lisp has something similar (via the load function), but how does one get a function I just defined and tested into a file to be saved? I'm hoping there's a better method than my current select+copy+paste.
Copy and paste in one thing. But the correct way is to work from a text file in an editor window. One can compile/load expressions, the editor buffer or the associated file.
How do you debug errors? Is there any ability to step into code like I would with other languages?
See STEP, TRACE and related. SLIME, LispWorks and Allegro CL have lots of additional features.
As long as the S-expression is valid, I don't get any errors when entering a (defun ...). It's not until I try to use it that I find out it's not valid. Is there any way to get errors sooner (i.e. compile the code)?
For many cases one uses a compiler. The compiler will find a range of errors and also will note when something is unusual (for example a function does not exist or a variable has not been defined).
-Is there some IDE that would be more familiar to me or allow me to play with the language easier?
LispWorks, Allegro CL are the best under Windows. There are some alternatives like Corman Lisp (I don't know it is maintained right now) or even Ufasoft Lisp.
Should I switch to learning Scheme instead?
Not really.
It doesn't sound like you're really using SLIME, or at least not in the way it was intended to be used. ("have to retype the defun", "the C model where you have code files")
I recommend watching some SLIME screencasts (or, even better, watching a Lisp programmer use SLIME for a few minutes, if you have one handy). The SLIME webpage has a couple.
It sounds like you'd really enjoy the DrRacket IDE. Racket is closer to Scheme than to Common Lisp, but you could dip your toes into the Lisp family without the speed bump of the Emacs style of development.

Contextual help in Emacs?

I am not a very good at using Emacs, but the feature I would like the most would be some integration with help/documentation for a particular language/API I use at the moment. I would imagine that there would be help displayed in another buffer depending on where I put my cursor while editing.
I wonder if there is a package that does that, even if it would be very simple, just displaying some file based on the keyword. I think there is, but I cannot find it ("help" is a too generic word).
(In particular, I would like to have this help for Common Lisp, but other languages, such as Java or C, could be useful.)
ILISP and SLIME provide several methods for looking up a function; see the Emacs wiki and the SLIME documentation. Or just built into Emacs itself, there are functions like C-h f to get function help or M-x man; both use the text at the point by default. You could pretty easily adapt them to work for another language of your choice.
Assuming you are using SLIME for common-lisp, you can take a look at slime-autodoc-mode.
Sorry, can't help with a generic solution for this.
You can set up the CLHS root for SLIME in your .emacs file:
(setq common-lisp-hyperspec-root "/usr/share/doc/hyperspec/HyperSpec/")
Adjust the path to where you put your HyperSpec.
Then, C-c C-d h with point at a symbol will look it up there in your browser.
One thing you might like to enable is eldoc-mode, by adding (turn-on-eldoc-mode) to your mode hook functions for the appropriate programming modes.
In ElDoc mode, the echo area displays information about a
function or variable in the text where point is. If point is
on a documented variable, it displays the first line of that
variable's doc string. Otherwise it displays the argument list
of the function called in the expression point is on.
This is probably less than you were after, but it still makes a good companion to a fuller-featured contextual help system, and there are a number of programming modes that support it.