call-process-chatgpt.md (9890B)
1 title: ChatGPT and Emacs Lisp 2 date: 2023-07-07 14:45 3 --- 4 # ChatGPT explaining Emacs Lisp 5 6 A perplexed friend asked ChatGPT what my code does. I shared it with 7 a bunch of people and a person on #systemcrafters-general:matrix.org 8 then suggested I ask ChatGPT for improvements. 9 10 ## Original 11 12 (progn 13 (defun kakafarm/call-process-with-string-as-input (program &optional input-string &rest args) 14 (with-temp-buffer 15 (let ((our-output-buffer (current-buffer))) 16 (if input-string 17 (with-temp-buffer 18 (let ((our-input-buffer (current-buffer))) 19 (progn 20 (erase-buffer) 21 (insert input-string) 22 (apply 'call-process-region 23 (buffer-end -1) 24 (buffer-end 1) 25 program 26 nil 27 our-output-buffer 28 nil 29 args)))) 30 (apply 'call-process 31 program 32 nil 33 our-output-buffer 34 nil 35 args))) 36 (buffer-string))) 37 38 (kakafarm/call-process-with-string-as-input "cat" 39 "cat says moo") 40 (kakafarm/call-process-with-string-as-input "echo" 41 nil 42 "echo echo echo")) 43 44 ## Explanation by ChatGPT 45 46 The code defines a function named kakafarm/call-process-with-string-as-input. This function takes three arguments: program, input-string, and args. It executes a command-line program (program) and returns the output as a string. The input-string argument is optional and allows passing input to the program. 47 48 The function starts by creating a temporary buffer using the with-temp-buffer macro. This buffer will be used to store the output of the command. The variable our-output-buffer is bound to the current buffer. 49 50 Next, there is a conditional statement that checks if an input-string is provided. If it is, another temporary buffer (our-input-buffer) is created to hold the input string. The erase-buffer function clears the our-input-buffer, and the insert function inserts the input-string into the buffer. 51 52 Then, the function call-process-region is called with arguments (buffer-end -1) and (buffer-end 1), which represent the beginning and end of the our-input-buffer. This function executes the specified program with the given input and redirects the output to our-output-buffer. The args are also passed to the call-process-region function. 53 54 If no input-string is provided, the function call-process is used instead. It directly executes the program with the given args, without any input. 55 56 After executing the command, the buffer-string function is called to retrieve the contents of the our-output-buffer. This value is then returned as the result of the function. 57 58 Finally, the function is invoked twice to demonstrate its usage. In the first invocation, the program "cat" is executed with the input string "cat says moo". In the second invocation, the program "echo" is executed without any input, but with the arguments "echo echo echo". 59 60 Overall, this code snippet defines a utility function that simplifies calling command-line programs and capturing their output in Lisp. It demonstrates the flexibility of Lisp in handling strings, buffers, and external processes. 61 62 ## Improvements by ChatGPT 63 ### Code 64 65 (defun kakafarm/call-process-with-string-as-input (program &optional input-string &rest args) 66 (if input-string 67 (with-temp-buffer 68 (insert input-string) 69 (apply 'call-process-region (point-min) (point-max) program nil t nil args)) 70 (apply 'call-process program nil t nil args))) 71 72 (list (kakafarm/call-process-with-string-as-input "cat" "cat says moo") 73 (kakafarm/call-process-with-string-as-input "echo" nil "-n" "echo echo echo")) 74 75 ### Explanation 76 77 Improvements: 78 79 Removed unnecessary progn wrapper around the defun. 80 Simplified the logic for handling input strings. No need for nested with-temp-buffer calls and separate buffer variables. 81 Replaced (buffer-end -1) and (buffer-end 1) with (point-min) and (point-max) respectively for clarity. 82 Replaced (buffer-string) with t in call-process-region to discard the output buffer and avoid unnecessary memory allocation. 83 Removed unnecessary nil argument in call-process. 84 These improvements make the code cleaner and more efficient. 85 86 ## Doom? 87 88 My friend asked if it make sense. Does it? 89 90 ### Running the code 91 92 (progn ; Adding a progn so I can run both expressions in one go. 93 (defun kakafarm/call-process-with-string-as-input (program &optional input-string &rest args) 94 (if input-string 95 (with-temp-buffer 96 (insert input-string) 97 (apply 'call-process-region (point-min) (point-max) program nil t nil args)) 98 (apply 'call-process program nil t nil args))) 99 100 (list (kakafarm/call-process-with-string-as-input "cat" "cat says moo") 101 (kakafarm/call-process-with-string-as-input "echo" nil "-n" "echo echo echo"))) 102 echo echo echo ; The result after running eval-last-sexp (C-x C-e). 103 104 I've expected a string return value of the whole progn expression, yet 105 what I've got was an insertion to this here buffer. 106 107 We are safe... 108 109 ... 110 111 for now. 112 113 ## Yes, we are safe. 114 115 https://chat.openai.com/share/08cc30e5-21ce-4549-9f3b-7de82d40f9b9 116 117 Copying it here: 118 119 Shared Chat• 120 Model: Default 121 Improve Lisp program. 122 July 7, 2023 123 can you improve this program please? 124 125 (progn 126 (defun kakafarm/call-process-with-string-as-input (program &optional input-string &rest args) 127 (with-temp-buffer 128 (let ((our-output-buffer (current-buffer))) 129 (if input-string 130 (with-temp-buffer 131 (let ((our-input-buffer (current-buffer))) 132 (progn 133 (erase-buffer) 134 (insert input-string) 135 (apply 'call-process-region 136 (buffer-end -1) 137 (buffer-end 1) 138 program 139 nil 140 our-output-buffer 141 nil 142 args)))) 143 (apply 'call-process 144 program 145 nil 146 our-output-buffer 147 nil 148 args))) 149 (buffer-string))) 150 151 (list (kakafarm/call-process-with-string-as-input "cat" 152 "cat says moo") 153 (kakafarm/call-process-with-string-as-input "echo" 154 nil 155 "-n" 156 "echo echo echo"))) 157 158 ChatGPT 159 160 Certainly! Here's an improved version of the program: 161 162 lisp 163 164 (defun kakafarm/call-process-with-string-as-input (program &optional input-string &rest args) 165 (if input-string 166 (with-temp-buffer 167 (insert input-string) 168 (apply 'call-process-region (point-min) (point-max) program nil t nil args)) 169 (apply 'call-process program nil t nil args))) 170 171 (list (kakafarm/call-process-with-string-as-input "cat" "cat says moo") 172 (kakafarm/call-process-with-string-as-input "echo" nil "-n" "echo echo echo"))) 173 174 Improvements: 175 176 Removed unnecessary progn wrapper around the defun. 177 Simplified the logic for handling input strings. No need for nested with-temp-buffer calls and separate buffer variables. 178 Replaced (buffer-end -1) and (buffer-end 1) with (point-min) and (point-max) respectively for clarity. 179 Replaced (buffer-string) with t in call-process-region to discard the output buffer and avoid unnecessary memory allocation. 180 Removed unnecessary nil argument in call-process. 181 182 These improvements make the code cleaner and more efficient. 183 I've expected a string return value of the whole progn expression, yet 184 what I've got was an insertion to this here buffer. 185 ChatGPT 186 187 Apologies for the misunderstanding. If you would like the whole progn expression to return a string instead of inserting it into a buffer, you can use the with-output-to-string macro. Here's the updated code: 188 189 lisp 190 191 (progn 192 (defun kakafarm/call-process-with-string-as-input (program &optional input-string &rest args) 193 (with-output-to-string 194 (if input-string 195 (with-input-from-string input-string 196 (apply 'call-process-region program nil standard-output nil args)) 197 (apply 'call-process program nil standard-output nil args)))) 198 199 (kakafarm/call-process-with-string-as-input "cat" "cat says moo")) 200 201 It had imagined a new form called 202 `with-input-from-string`. It does not work. 203 204 In this version, the with-output-to-string macro captures the output of the progn expression and returns it as a string. The standard-output stream is used as the output destination for the call-process-region or call-process functions, depending on whether an input string is provided. 205 206 Please note that the (kakafarm/call-process-with-string-as-input "echo" nil "-n" "echo echo echo") part from your original code has been removed since it wasn't necessary for demonstrating the changes. Feel free to add it back if needed. 207 Continue this conversation 208 | 209 Terms of use 210 | 211 Privacy policy 212 213 Improve Lisp program.