函数执行完毕后,如何退出 lisp 中的循环?

Pii*_*kyy 6 lisp function common-lisp

我是 LISP 的初学者,希望你能为我解决我的困惑。我的代码如下:

(defun retrieve (element closed)
  (if (= (length closed) 0)
      (setf closedlist '(a))
      (dolist (count closed)
        (when (equal element (car count))
          (progn (check (childvalue (symbol-value count)) count) 
                 (return)));;;endif
        );;;endouterloop
      )
  )
Run Code Online (Sandbox Code Playgroud)

这是第一个函数,它将接收一个名为“element”的对象和一个名为“close”的列表。下一个函数如下:

(defun check (child close)
  (setf tempvalue child)
  (dotimes (count (length tempvalue));;;1st loop
    (setf front (car tempvalue))
    (setf templist close)
    (dotimes (count1 (length close));;;2nd loop
      (if (= (length close) 1) 
          (if (string= front (car templist)) 
              ((remove (nth count) child) (return));;;true
              (setf templist (car templist));;;else
              )
          (if (string= front (car templist)) 
              (setf child (remove (nth count child) child))
              (setf templist (cdr templist));;;else
              )
          )
      );;;2nd loop
    (setf tempvalue (cdr tempvalue))
    );;;1stloop
  (format t "child ~S~%" child)
  )
Run Code Online (Sandbox Code Playgroud)

我的问题是,从第一个函数开始,当我在第一个函数内部时,如果满足条件,我将调用第二个函数(检查)。但是,在我从第一个函数(检索)调用第二个函数(检查)并成功执行操作后,我想从第一个函数退出 dotimes 循环,但我做不到。

如果我尝试添加(返回)它,程序将退出循环,而不执行语句内的其他操作。在这种情况下,(检查(childvalue(符号值temp))(第n个计数已关闭))。

有人可以提供有关如何在调用辅助函数后退出循环的建议吗?谢谢。

enr*_*rey 0

if有一个格式(if <condition> <if-true> <if-false>)

你写了(if <condition> (check ...) (break) ),所以它break处于该<if-false>位置,并且在条件为假时第一次消失。要将多个语句组合为一个,请使用progn.

(if (equal element temp)
    (progn (check (childvalue (symbol-value temp)) (nth count closed)) 
           (return)))
Run Code Online (Sandbox Code Playgroud)

除了将语句组合在一起并返回最后一个语句的结果之外,Progn 不执行任何操作。

您也可以使用when来代替if. When工作原理就像(when <condition> <if-true>... ). 它可以有多个 if-true,但不能有 if-false。我认为这非常适合你的情况。

为了完整起见, 的反义词whenunless。它有多个 if-false,没有 if-true。(unless cond ...)相当于(when (not cond) ...)

旁注:作为旁注,请将右括号放在同一行上,不要放在)单独的行上。您的编辑器应该为您缩进内容,然后只需通过缩进自行查找和导航,然后忘记那些右括号。一旦你开始这样做,代码就会看起来比许多传统语言更清晰。

第二边注意:如果您想要局部变量,请使用let,否则您会在某些实现中收到未声明的变量通知。例子:

(defun check (child close)
  (let ((tempvalue child)
        (front)
        (templist))
    (dotimes (count (length tempvalue))
      (setf front (car tempvalue))
      (setf templist close)
      (dotimes (count1 (length close))
        (if (= (length close) 1) 
            (if (string= front (car templist)) 
                ((remove (nth count) child) (return))
                (setf templist (car templist)))
            (if (string= front (car templist)) 
                (setf child (remove (nth count child) child))
                (setf templist (cdr templist)))))
      (setf tempvalue (cdr tempvalue)))
    (format t "child ~S~%" child)))
Run Code Online (Sandbox Code Playgroud)