Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > LISP > [CL] переменные внутри функции


Автор: anatox91 11.2.2012, 16:41
есть задача написать функцию на лиспе с тремя аргументами, которая формирует из них список и выполняет его обработку в соответствии с заданием

Код

Проверить, является ли второй элемент списка вещественным или рациональным числом. 
Если является, то поменять его на квадрат этого числа. 
Если не является, то вернуть исходный список без последнего элемента.
 

вот что получилось набросать:
Код

(defun func (x y z)
  (setf mylist (cons 'x (cons 'y (cons 'z nil))))
  (if (or (floatp (second mylist)) (rationalp (second mylist))) 
      (setf (second mylist) (* (second mylist) (second mylist)))
      (butlast mylist))
  )

но этот код почему-то не работает
когда вызываю функцию как
Код

(func 1 2.0 3)

или
Код

(func 1 23/56 4)


 то ничего не выводит
плюс был варнинг что mylist is undefined variable
в чем может быть проблема?
заранее извиняюсь если что, только начал изучать лисп

P.S. eclipse indigo + cups

Автор: anatox91 11.2.2012, 19:08
все, проблема решена, чуть переписал функцию 
Код

(defun func (x y z)
  (setq mylist (list x y z))
  (if (or (floatp (second mylist)) (rationalp (second mylist))) 
      (setf (second mylist) (* (second mylist) (second mylist)))
      (setf mylist (butlast mylist)))
  (print mylist)



и в другой среде (LispWorks) все отлично заработало

Автор: tzirechnoy 11.2.2012, 21:06
1) И за setf, и за setq в чистых функцыях (от которых не требуется побочных эффектов) надо бить по рукам.
2) За засорение простых имён вроде mylist когда не просят -- второй раз бить по рукам.
3) У функцыи print есть побочные эффекты, которых никто не просил.
Кроме того, выдать значение переменной можно просто написав имя этой переменной. Без скобок. И если это последний оператор в форме -- то его значение и будет результатом формы.

Автор: k0rvin 13.2.2012, 08:33
Код

(defun func (x y z)
  (let* ((xyz    (list x y z))
         (second (second xyz)))
    (if (or (rationalp second)
            (floatp    second))
        (list (first xyz)
              (expt second 2)
              (third xyz))
        (butlast xyz))))

Автор: anatox91 19.2.2012, 15:18
да я уже понял все это, просто то было самое первое что пытался написать на лиспе, не привыкнув к функциональному программированию, пытался использовать лисп как с++
теперь уже потихоньку осваиваюсь

Автор: k0rvin 20.2.2012, 07:58
Цитата(anatox91 @ 19.2.2012,  15:18)
да я уже понял все это, просто то было самое первое что пытался написать на лиспе, не привыкнув к функциональному программированию, пытался использовать лисп как с++
теперь уже потихоньку осваиваюсь

При чем тут функциональное программирование? Мой пример переписывается на C++/C/Pascal/whatever один в один

Автор: _sg 22.2.2012, 10:32
Код

(defun square2nd-or-remove3rd (a b c)
  (if (realp b) (list a (expt b 2) c) (list a b)))

> (square2nd-or-remove3rd 1 2.2 3)
(1 4.84 3)

Автор: _sg 25.4.2014, 16:15
Код

(defun square2nd-or-remove3rd (a b c)
  (if (realp b) `(,a ,(expt b 2) ,c) `(,a ,b)))

> (square2nd-or-remove3rd 1 2.2 3)
(1 4.84 3)

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)