Научите лиспу на примере (или как kpblc, VVA и компания пытаются обучить чайника лиспу) - Страница 225
| Правила | Регистрация | Пользователи | Сообщения за день |  Справка по форуму | Файлообменник |

Вернуться   Форум DWG.RU > Программное обеспечение > Программирование > LISP > Научите лиспу на примере (или как kpblc, VVA и компания пытаются обучить чайника лиспу)

Научите лиспу на примере (или как kpblc, VVA и компания пытаются обучить чайника лиспу)

Ответ
Поиск в этой теме
Непрочитано 20.07.2008, 20:12 1 |
Научите лиспу на примере (или как kpblc, VVA и компания пытаются обучить чайника лиспу)
Red Nova
 
ՃԱՐՏԱՐԱԳԵՏ, տ.գ.թ.
 
Торонто
Регистрация: 23.10.2007
Сообщений: 1,990

Со школы не ладится у меня с программированием. Все предметы щелкал, а на экзамене по информатике (Visual foxpro) программку типа суммирования столбцов списал у соседа (это уже в университете).
Не смотря на эте намерен научится писать программы для Автокада на лиспе, скачал книгу Хювенена, несколько примеров создания программ, но после получасового “смотрения” таких книг мое мышление явно притормаживает.
Решил пойти другим путем.
Нашел самый короткий лисп из моей коллекции, и прошу программистов с этого форума пошагово объяснить какой символ что означает. Надеюсь на вашу помощь.


Код:
[Выделить все]
(defun c:make-blocks-explodeable (/ adoc)
  (vl-load-com)
  (vla-startundomark
    (setq adoc (vla-get-activedocument (vlax-get-acad-object)))
    ) ;_ end of vla-startundomark
  (vlax-for blk_def (vla-get-blocks adoc)
    (if (and (equal (vla-get-isxref blk_def) :vlax-false)
             (equal (vla-get-islayout blk_def) :vlax-false)
             ) ;_ end of and
      (vl-catch-all-apply '(lambda () (vla-put-explodable blk_def :vlax-true)))
      ) ;_ end of if
    ) ;_ end of vlax-for
  (vla-endundomark adoc)
  (princ)
  ) ;_ end of defun
_____________________________________________________________________________________________________________

Прошло много лет и топик теперь представляет из себя площадку для обучения азов программирования для многих начинающих.
Так что начинающие лиспогрызы приветствуются .
__________________
Блог

Последний раз редактировалось Red Nova, 12.07.2017 в 05:43.
Просмотров: 2048267
 
Непрочитано 01.11.2023, 17:14
#4481
koMon


 
Блог
 
Регистрация: 26.09.2017
Сообщений: 1,809


Цитата:
Сообщение от gnuvse Посмотреть сообщение
просто чертим pline по вставленным блокам
добавляем полилинию по точкам вставки выбранных блоков?

----- добавлено через ~2 мин. -----
Цитата:
Сообщение от gnuvse Посмотреть сообщение
1. Есть ли встроенная функция по декодированию списка-списков в список?
(apply 'append '((1 2 3) (4 5 6) (7 8 9)))-> '(1 2 3 4 5 6 7 8 9)
__________________
K Lisp
koMon вне форума  
 
Непрочитано 01.11.2023, 18:42
#4482
gnuvse


 
Регистрация: 13.04.2017
Сообщений: 136


Цитата:
Сообщение от Кулик Алексей aka kpblc Посмотреть сообщение
Код:
[Выделить все]
 ; собираем список всех точек из списка-списков точек. Было ((x y z)...(xn yn zn)) -> (x y z ... xn yn zn)
	(defun list-of-lists-pt->list (point-list)
    (apply (function append) point-list))
И вторую я бы написал примерно так:
Код:
[Выделить все]
 (defun list-pt->safearray (list-pt) 
  (vlax-vlax-safearray-fill 
    (vlax-make-safearray 
      vlax-vbDouble
      (cons 0 (1- (length list-pt)))
      list-pt
    )
  )
)


Какой же это изящный чит с append.
Переписал свою функцию для получения cписка точек из vla-list-bl в духе Lisp

Код:
[Выделить все]
 
(defun get-list-of-lists-pts (vla-set-of-bl)
	(setq list-of-lists-pt 
		(mapcar
			(function 
				(lambda (vla-bl) 
					(vlax-get vla-bl "insertionpoint")
				)
			)
			vla-set-of-bl
		)
	)
	list-of-lists-pt
)
А что касается массива, то я пока пишу чуть подробней, чтобы понимать как оно работает. А так да, все друг в друга вкладывается и каждый вызов передает значение в другую функцию.

Лех, спасибо.
Если у тебя будет чуть больше времени и вдруг станет жалко нуба в виде меня, пожалуйста ответь на другие вопросы.

----- добавлено через ~2 мин. -----
Цитата:
Сообщение от koMon Посмотреть сообщение
добавляем полилинию по точкам вставки выбранных блоков?

----- добавлено через ~2 мин. -----

(apply 'append '((1 2 3) (4 5 6) (7 8 9)))-> '(1 2 3 4 5 6 7 8 9)
Да, все верно.
Спасибо за append, мне Леха подсказал уже, классная штука
gnuvse вне форума  
 
Непрочитано 01.11.2023, 20:50
1 | #4483
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 40,406


Цитата:
Сообщение от gnuvse Посмотреть сообщение
Это определение этого места, то есть на пути от одной точки до другой стоит некое препятствие, может можно какой-то тестовый луч перед построением отправлять?
Чисто теоретически (если не привлекать тяжелую артиллерию в виде R-Tree, про которое несколько раз упоминал trir), то можно попытаться пройтись по всем примитивам и получить от них BoundingBox. Строим пары точек будущей полилинии и смотрим, пересекает ли каждый из этих "виртуальных" отрезков прямоугольник примитива (ну или, в некоторых случаях, сам примитив) - см. inters. Логика так себе, согласен - может, кто и подскажет более приемлемый способ для лиспа.
Чего еще хотелось бы добавить. Точки вставки у тебя будут трехмерные, а координаты в полилинию надо передавать двумерные. Вариантов немного - либо каждую координату принудительно приводить к двумерному виду, либо создавать полилинию через entmake / entmakex. Второй вариант будет работать только в текущем документе, учти.
__________________
Моя библиотека lisp-функций
---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 02.11.2023, 10:03
#4484
gnuvse


 
Регистрация: 13.04.2017
Сообщений: 136


Цитата:
Сообщение от Кулик Алексей aka kpblc Посмотреть сообщение
Чисто теоретически (если не привлекать тяжелую артиллерию в виде R-Tree, про которое несколько раз упоминал trir), то можно попытаться пройтись по всем примитивам и получить от них BoundingBox. Строим пары точек будущей полилинии и смотрим, пересекает ли каждый из этих "виртуальных" отрезков прямоугольник примитива (ну или, в некоторых случаях, сам примитив) - см. inters. Логика так себе, согласен - может, кто и подскажет более приемлемый способ для лиспа.
Чего еще хотелось бы добавить. Точки вставки у тебя будут трехмерные, а координаты в полилинию надо передавать двумерные. Вариантов немного - либо каждую координату принудительно приводить к двумерному виду, либо создавать полилинию через entmake / entmakex. Второй вариант будет работать только в текущем документе, учти.
Спасибо. Ничего себе, я думал будет чуть попроще.
Сейчас только осознал, что если эксплуатировать мою программу, то проще будет просто ставить лишний мнимый блок на угол или подкорректировать линию.
Потому что как это все будет работать с xref непонятно, он же не примитив.

А можешь подсказать какие из твоих исходников я мог бы начать изучать?
gnuvse вне форума  
 
Непрочитано 02.11.2023, 11:55
#4485
koMon


 
Блог
 
Регистрация: 26.09.2017
Сообщений: 1,809


gnuvse,
добавить 2d-полилинию по точкам вставки выбранных блоков
Код:
[Выделить все]
 
(setq raw_vertices_list (apply 'append 
							   (mapcar '(lambda (ename) (cdr (assoc 10 (entget ename)))) 
										(vl-remove-if 'listp 
											(mapcar 'cadr (ssnamex (ssget '((0 . "insert")))))
										)
							   )
						)
)
(vla-addpolyline (vla-get-block (vla-get-activelayout (vla-get-activedocument (vlax-get-acad-object))))
 				 (vlax-safearray-fill 
				 	(vlax-make-safearray vlax-vbdouble (cons 1 (length raw_vertices_list))) 
					raw_vertices_list
				 )
)
__________________
K Lisp
koMon вне форума  
 
Непрочитано 02.11.2023, 12:56
#4486
gnuvse


 
Регистрация: 13.04.2017
Сообщений: 136


Цитата:
Сообщение от koMon Посмотреть сообщение
gnuvse,
добавить 2d-полилинию по точкам вставки выбранных блоков
Код:
[Выделить все]
 
(setq raw_vertices_list (apply 'append 
							   (mapcar '(lambda (ename) (cdr (assoc 10 (entget ename)))) 
										(vl-remove-if 'listp 
											(mapcar 'cadr (ssnamex (ssget '((0 . "insert")))))
										)
							   )
						)
)
(vla-addpolyline (vla-get-block (vla-get-activelayout (vla-get-activedocument (vlax-get-acad-object))))
 				 (vlax-safearray-fill 
				 	(vlax-make-safearray vlax-vbdouble (cons 1 (length raw_vertices_list))) 
					raw_vertices_list
				 )
)

Так у меня уже в коде все написано, я скидывал рабочий вариант черчения линии.
Может ты сможешь посоветовать какие исходники поизучать, буду благодарен?
gnuvse вне форума  
 
Непрочитано 02.11.2023, 12:57
1 | #4487
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 40,406


Цитата:
Сообщение от gnuvse Посмотреть сообщение
А можешь подсказать какие из твоих исходников я мог бы начать изучать?
Не-а... У меня нормальных исходников-то практически нет. Могу посоветовать "САПР на базе" (в глубинах форума где-то скан есть). Можно сказать библия разработчика под кад ))
__________________
Моя библиотека lisp-функций
---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 02.11.2023, 13:17
1 | #4488
koMon


 
Блог
 
Регистрация: 26.09.2017
Сообщений: 1,809


Цитата:
Сообщение от gnuvse Посмотреть сообщение
какие исходники поизучать
изучать лисп по исходникам - дело неблагодарное) лучше смотреть что может делать лисп, activex и применять эти знания к решению своих задач.
__________________
K Lisp
koMon вне форума  
 
Непрочитано 02.11.2023, 15:02
#4489
Сергей812


 
Регистрация: 10.08.2013
Сообщений: 11,499


ну и быть моральным готовым к тому - что в один прекрасный момент "упретесь" в то же быстродействие лиспа, когда уже будет готов определенный объем программы)
Сергей812 вне форума  
 
Непрочитано 02.11.2023, 15:09
#4490
gnuvse


 
Регистрация: 13.04.2017
Сообщений: 136


Цитата:
Сообщение от Сергей812 Посмотреть сообщение
ну и быть моральным готовым к тому - что в один прекрасный момент "упретесь" в то же быстродействие лиспа, когда уже будет готов определенный объем программы)
Я не программист, не думаю, что для моих тривиальных задач это будет проблемой.

----- добавлено через 46 сек. -----
Цитата:
Сообщение от koMon Посмотреть сообщение
изучать лисп по исходникам - дело неблагодарное) лучше смотреть что может делать лисп, activex и применять эти знания к решению своих задач.
А, тут дело в том, чтобы смотреть в комплексе и на код и Doc, потому что читать тоже полезно.
gnuvse вне форума  
 
Непрочитано 09.11.2023, 07:39
#4491
40in


 
Регистрация: 24.03.2011
Сообщений: 14


Добрый день!
Имеется такой кусок программы:
Код:
[Выделить все]
 (setq obj nil)
(while (or (= obj nil)
	   (/= (cdr (assoc 0 (entget obj))) "TEXT")
;;;	   (/= (cdr (assoc 0 (entget obj))) "MULTILEADER")
       )
  (setq obj (car (entsel)))
)
По двум условиям все работает, но если включить третье условие то ничего не работает. Что не так?
40in вне форума  
 
Непрочитано 09.11.2023, 09:37
#4492
koMon


 
Блог
 
Регистрация: 26.09.2017
Сообщений: 1,809


40in,
Код:
[Выделить все]
 
(setq obj nil)
(while (or (null obj)
	   	   (and
		   		(/= (cdr (assoc 0 (entget obj))) "TEXT")
	   	   		(/= (cdr (assoc 0 (entget obj))) "MULTILEADER")
		   )
       )
  	   (setq obj (car (entsel)))
)
__________________
K Lisp
koMon вне форума  
 
Непрочитано 09.11.2023, 09:49
#4493
40in


 
Регистрация: 24.03.2011
Сообщений: 14


Спасибо большое! Ну не програмер я...)))))
40in вне форума  
 
Непрочитано 03.12.2023, 00:22
#4494
posetitel


 
Регистрация: 16.10.2013
Сообщений: 395


Товарищи, подскажите, возможно ли в принципе на лисп реализовать вот такую хотелку.
1) Есть в чертеже несколько поллиний, каждая полилиния в своем слое (например слой1, слой2, слой3). Я хочу секущей рамкой выбрать определенные полилинии, например, выбрал полилинию, находящуюся в слой1, и полилинию, находящуюся в слой3, и запомнить выбор в какую-нибудь переменную (тут вроде все выполнимо).
2) Далее необходимо во вторую переменную из заранее заготовленного экселя подгрузить таблицу соответствия величины диаметра названию всех слоев с полилиниями на чертеже.
Ну т.е. в экселе в первом столбце названия слоев, а во втором столбце величина диаметра, получается слой1=10, слой2=20, слой3=30.
3) Далее внутри лиспа выполнить функцию, аналогичную функции экселя ВПР, т.е. соотнести слои из переменной 1 и слои в переменной 2, и в случае совпадения имен создать переменную 3, в которой будут уже не названия слоев, а числа соответствующие диаметрам каждого слоя (в примере получается 2 числа: 10 и 30).
4) Ну и самое простое - начертить кружочки с диаметрами из переменной 3.
Теоретически, наверное, это реализуемо, если сначала выгрузить переменную 1 из действия 1) в эксель, уже в экселе с функцией ВПР обработать результат, там же сформировать команду черчения окружностей и потом просто скопировать готовую команду черчения окружностей в командную строку, но хотелось миновать задействования экселя в процессе работы лиспа.

Смущают пункты 2 и 3, на VBA я сопоставление и выборку сделать смогу, а вот можно ли так на лиспе?

Последний раз редактировалось posetitel, 03.12.2023 в 11:48.
posetitel вне форума  
 
Непрочитано 03.12.2023, 12:07
1 | #4495
Сергей812


 
Регистрация: 10.08.2013
Сообщений: 11,499


имхо, вместо экселя загружать из текстового файла в список точечные пары {имя слоя . диаметр}, и потом искать в этом списке по имени слоя. Т.е. в текстовом файле идет построчно имя слоя и на следующей строке сопоставленный слою диаметр. И тогда сформировать список примерно таким кодом:
Код:
[Выделить все]
 (setq lF (open "%FileName%" "r"))
   (while (and lKey lD)
      (setq lKey (read-line lF))
      (setq lD (read-line lF))
      (if (and lKey lD) (setq lLst (append lLst (List (cons lKey lD)))))
   )
   (close lF)
и на выходе в переменной lLst будет список пар типа (("Name1" . 10) ("Name2" . 20) ("Name3" . 30)).

Ну а получить потом из списка диаметр
Код:
[Выделить все]
 (setq lD (cdr (assoc %Имя слоя%  lLst)))
естественно, это все надо "обвесить" проверками на получение не NIL значения и обработчиками ошибок.

Последний раз редактировалось Сергей812, 03.12.2023 в 13:00. Причина: добавлен пример кода
Сергей812 вне форума  
 
Непрочитано 03.12.2023, 15:51
#4496
posetitel


 
Регистрация: 16.10.2013
Сообщений: 395


В лиспе совсем-совсем новичок, сижу с рекомендуемой всем новичкам в этой теме талмудом на 1000 страниц и пытаюсь разобрать код, но все равно идет трудновато. Направьте в нужное русло, тем более тема соответствующая.
В общих чертах смысл первого кода ясен: пока в текстовом документе есть строчки, в переменную lLst слепляются точечные пары. Но хочу детально вникнуть, что делает каждая функция и тут затык получается.
Непонятно выражение (while (and lKey lD). Ну т.е. я представляю, как оно обычно работает, но вот как конкретно в этом коде не догоняю.
Переменные lKey lD, если их не объявить перед функцией while, сразу выдадут nil и цикл должен прерваться. В чем я заблуждаюсь в своих рассуждениях?
Еще уточняющий вопрос: функция read-line автоматически перескакивает на следующую строчку? Т.е. выражения
(setq lKey (read-line lF))
(setq lD (read-line lF))
сами читают строчки по очереди, не надо добавлять что-то вроде next read-line или read-line = read-line+1 ?
Ну и самый важный вопрос от новичка: а как у вас получаются цветные слова? Как можно писать и обкатывать код на лиспе? А то я по старинке в блокноте пишу, потом пока загружу в автокад, пока напишу команду на выполнение...
posetitel вне форума  
 
Непрочитано 03.12.2023, 16:03
1 | #4497
Сергей812


 
Регистрация: 10.08.2013
Сообщений: 11,499


Цитата:
Сообщение от posetitel Посмотреть сообщение
функция read-line автоматически перескакивает на следующую строчку
да, т.е. она "проглатывает" символы конца текущей строки и указатель файла (это уже не к лиспу, а к самой операционной системе относится) стоит на начале следующей строки. А если файл закончился, то вернет nil. Ну для красоты перед вторым вызовом (setq lD (read-line lF)) можно было бы сперва проверить lKey <> nil - чтобы не пытаться читать завершенный файл еще раз.

Цитата:
Сообщение от posetitel Посмотреть сообщение
(while (and lKey lD)
если были успешно считаны обе связанные строки - в цикле пытаемся считать следующую пару значений. То же условие в строке 5 - если конец файла (или "накосячили" в файле и непарное количество значений), то просто не будет добавлено в список. Еще могут быть пустые строки в файле - тоже по хорошему их надо пропускать.

----- добавлено через ~2 мин. -----
ну вопрос валидации содержимого файла можно для упрощения проигнорировать - если это продукт для "личного" пользования.
Сергей812 вне форума  
 
Непрочитано 03.12.2023, 16:51
#4498
posetitel


 
Регистрация: 16.10.2013
Сообщений: 395


Цитата:
Сообщение от Сергей812 Посмотреть сообщение
если были успешно считаны обе связанные строки - в цикле пытаемся считать следующую пару значений. То же условие в строке 5 - если конец файла (или "накосячили" в файле и непарное количество значений), то просто не будет добавлено в список. Еще могут быть пустые строки в файле - тоже по хорошему их надо пропускать.
я к тому, не надо ли переписать вот так:
(setq lKey (read-line lF))
(setq lD (read-line lF))
(while (and lKey lD)
(if (and lKey lD) (setq lLst (append lLst (List (cons lKey lD)))))
(setq lKey (read-line lF))
(setq lD (read-line lF))
)
чтобы перед циклом сначала были заданы переменные, которые уже считали по строчке из текстового файла.
posetitel вне форума  
 
Непрочитано 03.12.2023, 17:57
1 | 1 #4499
Сергей812


 
Регистрация: 10.08.2013
Сообщений: 11,499


кстати да, не заметил логической ошибки, спасибо) Можно просто перед циклом вставить
Код:
[Выделить все]
 (setq lKey "" lD 1)
чтобы начальные значения не nil были и цикл хоть раз бы отработал.
Сергей812 вне форума  
 
Непрочитано 03.12.2023, 18:53
#4500
posetitel


 
Регистрация: 16.10.2013
Сообщений: 395


Это Вам спасибо за разъяснения кода.
А как код можно быстро тестировать и писать с цветовым выделением переменных, функций, чтобы нагляднее было?
posetitel вне форума  
Ответ
Вернуться   Форум DWG.RU > Программное обеспечение > Программирование > LISP > Научите лиспу на примере (или как kpblc, VVA и компания пытаются обучить чайника лиспу)



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
LISP. Вставка в таблицу поля, соотвествующего площади примитива Profan Готовые программы 272 06.06.2021 23:12
Сейсмозащита и сейсмоизоляция существующих, построенных зд. IANationalInformAgentstvo Прочее. Архитектура и строительство 216 20.01.2015 16:51
Мониторы LCD CRT Разное 94 17.06.2008 10:51
ЮМОР 2006 =) Perezz!! Разное 1122 04.01.2007 00:46