dwg.ru forum rss xml
| Правила | Регистрация | Пользователи | Поиск | Сообщения за день | Все разделы прочитаны |  Справка по форуму |

Вернуться   Форум DWG.RU > Программное обеспечение > Программирование > Перевод имени блока в имя переменной и обратно

Перевод имени блока в имя переменной и обратно

Версия для печати
 
Ответ
Опции темы Поиск в этой теме
Непрочитано 11.12.2009, 17:32 #1
Перевод имени блока в имя переменной и обратно
Supermax
 
Руководитель фирмы
 
Москва
Регистрация: 28.03.2007
Сообщений: 1,831
Отправить сообщение для Supermax с помощью Skype™

Supermax вне форума Вставить имя

Когда надо подсчитывать количество блоков данной конфигурации в моделе, надо обрабатывать эту модель и куда-то складывать результат обработки по конкретному блоку. Во всяком случае всегда стает вопрос как складировать данные. Я не бог, но у меня появилась бредовая идея перерабатывать имя блока, хоть *Unnn, хоть "Клапан односедельный запорно-регулирующий КЗР-80" в такое имя переменной, чтобы я мог потом, зная имя блока найти ту переменную, куда я складываю о таких блоках сведения.
Не судите меня строго, что мог, то и наваял.

Функция, превращающая строку с именем блока в имя переменной:

Код:
[Выделить все]
(defun block-name->variable-name (name / s n w)
(setq s nil)
(setq n 1)
(mapcar '(lambda (a)
 (if (= a 32) (setq s (append s (list n))))
  (setq n (1+ n)))
(vl-string->list name))
(setq n 0)
(setq w (vl-list->string (vl-remove-if '(lambda (a) (setq n (1+ n)) (member n s))
  (vl-string->list name))))
(setq w (vl-string-translate "." "/" w))
(setq w (vl-string-translate "'" "`" w))
(setq w (strcat w "Q" (apply 'strcat (mapcar '(lambda (a) (if (= (strlen a) 1) (strcat "0" a) a)) (mapcar 'itoa s)))))
)
Принцип прост. Запоминаем где в строке пробелы и удаляем их из строки. Затем к концу строки добавляем букву (я добавил Q, типа Quit) и далее куча цифр, которые говорят о том, где у нас в строке пробелы были. По два знака на одну позицию. 99 пробелов в названии, я думаю, редко встречается. Буква вставлена потому, что имя блока может и цифрой заканчиваться.

Из строки
"Клапан односедельный запорно-регулирующий КЗР-80"
получается
"Клапанодноседельныйзапорно-регулирующийКЗР-80Q072142"

Дешифрация производится так:
Читаем с конца все цифры до буквы и восстанавливаем строку уже с пробелами. Если строка начинается с *, то возвращается все, что получилось после дешифрации (все буквы в верхнем регистре), а если нет - лезем в коллекцию "Блоки" и достаем от туда имя по нашему дешифрированному коду. Он весь в верхнем регистре, а имя в разных.
Концовку можно и переписать. Мне именно так и надо. А вам - как хотите.

Дешефрация делается для того, что в этой переменной могут держаться не только указатели, а просто цифры, и зная переменную можно всегда найти сам блок дешефровав название этой переменной.

Функция дешефрации переменной в имя блока:
Код:
[Выделить все]
(defun variable-name->block-name (vname / n s w w1)
(vl-load-com)
(setq actdoc (vla-get-ActiveDocument (vlax-get-acad-object)))
(setq modeltxt (vla-get-ModelSpace actdoc))
(setq blocktxt (vla-get-Blocks actdoc))
(setq n (vl-position 81 (reverse (vl-string->list vname))))
(setq s nil)
(mapcar '(lambda (a) (if (/= n 0) (progn (setq s (append s (list a))) (setq n (1- n))))) (reverse (vl-string->list vname)))
(setq s (reverse s))
(setq n (/ (length s) 2))
(setq w nil)
(repeat n (setq w (append w (list (read (strcat (chr (car s)) (chr (cadr s))))))) (setq s (cddr s)))
(setq w1 nil)
(setq n 0)
(mapcar '(lambda (a) (setq n (1+ n)) (if (= n (car w)) 
                                                           (progn (setq w1 (append w1 (list 32) (list a))) (setq n (1+ n))(setq w (cdr w)))
                                                           (setq w1 (append w1 (list a)))
                                                         )
               ) (reverse (cdr (member 81 (reverse (vl-string->list vname)))))
)
(setq w1 (vl-list->string w1))
(setq w1 (vl-string-translate "/" "." w))
(setq w1 (vl-string-translate "`" "'" w))
(if (= (ascii w1) 42) w1
(vla-get-Name (vla-Item blocktxt w1)))
)
Откорректировал обе функции.
Апостроф заменяем тильдой, а потом обратно, а точку - косой чертой, а потом обратно.

Пару строк для работы:

Запись в переменную имя блока из которого она и сделана
Код:
[Выделить все]
(set (read (BLOCK-NAME->VARIABLE-NAME "Клапан односедельный запорно-регулирующий КЗР-80")) "Клапан односедельный запорно-регулирующий КЗР-80")
Чтение имени блока через дешифрацию названия переменной
Код:
[Выделить все]
(variable-name->block-name (vl-symbol-name 'Клапанодноседельныйзапорно-регулирующийКЗР-80Q072142))
Если у кого есть другие идеи как создавать имена переменных при обработке блоков - буду рад услышать (точнее увидеть).

Последний раз редактировалось Supermax, 14.12.2009 в 12:46.
Просмотров: 3269
 
Непрочитано 11.12.2009, 21:47
#2
Vov.Ka


 
Регистрация: 21.07.2008
Луцьк
Сообщений: 144


что делать если в имени блока есть "." или "'" ?
Vov.Ka вне форума вставить имя Обратить внимание модератора на это сообщение  
 
Автор темы   Непрочитано 11.12.2009, 22:02
#3
Supermax

Руководитель фирмы
 
Регистрация: 28.03.2007
Москва
Сообщений: 1,831
Отправить сообщение для Supermax с помощью Skype™


Ну, точки в имени не запрещены, а вот с ' действительно, прокол. Буду думать. Главное тильда в имени блока запрещена ` а одиночная кавычка ' нет. А в имени переменной запрещена кавычка, а тильда - лезет. По моему это кто-то, что-то напутал в Аутодеске.
Но ничего не поделаешь - придется выкручиваться. Буду, наверное, кавычку менять на тильду, раз ее в имени блока никогда нет (запрещена), а потом менять тильду на кавычку назад.
Завтра доделаю.
Supermax вне форума вставить имя Обратить внимание модератора на это сообщение  
 
Непрочитано 11.12.2009, 22:22
#4
Vov.Ka


 
Регистрация: 21.07.2008
Луцьк
Сообщений: 144


это насчет точки
Код:
Vov.Ka вне форума вставить имя Обратить внимание модератора на это сообщение  
 
Непрочитано 11.12.2009, 22:27
#5
Кулик Алексей aka kpblc
Moderator

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


Если честно, я не очень понял конечной цели этих телодвижений... Как разминка - да, покатит. Но для работы - зачем? Зачем плодить массу переменных, когда можно все "загнать" в список / массив?
__________________

---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума вставить имя Обратить внимание модератора на это сообщение  
 
Автор темы   Непрочитано 14.12.2009, 12:56
#6
Supermax

Руководитель фирмы
 
Регистрация: 28.03.2007
Москва
Сообщений: 1,831
Отправить сообщение для Supermax с помощью Skype™


Функции откорректировал. Апостроф заменяю тильдой, а потом обратно произвожу замену, а точку заменяю косой чертой с обратной заменой при востановлении имени блока.
Можно еще что-нибудь заменить. В блоках и = и <> и пр. запрещены в наименованиях, так что запас еще есть.

Кулик Алексей aka kpblc,
Массивы вещь хорошая, когда знаешь что искать. Тут проблема, что ты не знаешь ЧТО надо искать, точнее тебе не известен ориентир, по которому лежит запись. Тебе ее надо дополнить, или сократить, а ты даже не знаешь номера в массиве. В массив без знания где и что лежит лезть безсмысленно. Можно конечно в начало списка вставлять имя блока, а потом искать каждый раз перелопачивая весь массив, но можно и список имен переменных создать, а потом ему мапкаром nil прописать.
Кто что плодит, кто переменные, а кто берет одну переменную и закачивает в нее данные всей модели. Кому как удобно.
Supermax вне форума вставить имя Обратить внимание модератора на это сообщение  
 
Непрочитано 14.12.2009, 12:56
#7
Profan

Чужой
 
Регистрация: 25.12.2005
Москва
Сообщений: 13,667


Сбой питания или AutoCAD завис - и прощай переменные.
Profan вне форума вставить имя Обратить внимание модератора на это сообщение  
 
Непрочитано 14.12.2009, 13:22
#8
Do$

AutoCAD/Civil3D LISP/C#
 
Регистрация: 15.08.2008
Санкт-Петербург
Сообщений: 1,641
Отправить сообщение для Do$ с помощью Skype™


Цитата:
Сообщение от Supermax Посмотреть сообщение
Тут проблема, что ты не знаешь ЧТО надо искать, точнее тебе не известен ориентир, по которому лежит запись.
Код:
[Выделить все]
 
(setq block_attribute_list
       (list (cons "block name 1"
     (list "attribute11" "attribute12" "attribute13" "attribute14")
      ) ;_ end of cons
      (cons "block name 2"
     (list "attribute21" "attribute22" "attribute23")
      ) ;_ end of cons
      (cons "block name 3"
     (list "attribute31" "attribute32" "attribute33")
      ) ;_ end of cons
      (cons "block name 4"
     (list "attribute41" "attribute42" "attribute33")
      ) ;_ end of cons
       ) ;_ end of list
) ;_ end of setq
 
(assoc "block name 3" block_attribute_list)
Do$ вне форума вставить имя Обратить внимание модератора на это сообщение  
 
Непрочитано 14.12.2009, 14:06
#9
Кулик Алексей aka kpblc
Moderator

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


Supermax, у меня четкое ощущение, что ты пытаешься сделать очередной вариант bcount'a...
__________________

---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума вставить имя Обратить внимание модератора на это сообщение  
 
Непрочитано 14.12.2009, 14:47
#10
VVA

Инженер LISP
 
Регистрация: 11.05.2005
Минск
Сообщений: 6,690
Отправить сообщение для VVA с помощью ICQ Отправить сообщение для VVA с помощью Skype™


Цитата:
Сообщение от Supermax Посмотреть сообщение
Тут проблема, что ты не знаешь ЧТО надо искать, точнее тебе не известен ориентир, по которому лежит запись
Пример приведен в #8. Подсказка - ассоциативный список. Пример - то, что возвращает (entget(entlast)). В поле 210 лежит вектор нормали, а в поле 1 - имя блока. У тебя вместо цифр могут бать тэги атрибутов или имя блока+ тэг атрибута+название динамического свойства и т.д.
*** Добавлено ***

Код:
[Выделить все]
;; Get all attributes include constant attributes
  (vl-load-com)
  (defun get-all-atts (/ atts att_list const_atts const_list ent obj)
    (and (setq ent (car (entsel "\nSelect block to make attributes list: ")))
	 (setq obj (vlax-ename->vla-object ent))
	 (if (and (vlax-property-available-p obj 'Hasattributes)
		  (eq :vlax-true (vla-get-hasattributes obj))
	     )
	   (progn
	     (setq atts (vlax-invoke obj 'Getattributes))
	     (foreach att atts
	       (setq att_list
		      (cons (cons (vla-get-tagstring att)
				  (vla-get-textstring att)
			    )
			    att_list
		      )
	       )
	     )
	   )
	 )
    )
    (cond ((vlax-method-applicable-p obj 'Getconstantattributes)
	   (setq const_atts (vlax-invoke obj 'Getconstantattributes))
	   (foreach att	const_atts
	     (setq const_list
		    (cons (cons	(strcat "*CONSTANT*: " (vla-get-tagstring att))
				(vla-get-textstring att)
			  )
			  const_list
		    )
	     )
	   )
	   (setq att_list (append const_list att_list))
	  )
	  (T att_list)
    )
  )
;CaLL:(setq blk_info (get-all-atts))
__________________
Как использовать код на Лиспе читаем здесь
VVA вне форума вставить имя Обратить внимание модератора на это сообщение  
 
Автор темы   Непрочитано 14.12.2009, 15:45
#11
Supermax

Руководитель фирмы
 
Регистрация: 28.03.2007
Москва
Сообщений: 1,831
Отправить сообщение для Supermax с помощью Skype™


Понимаете, беда в том, что у меня нет такого списка.
Я выбрал не соглашение о переменных среды, а соглашение о принципах формирования таких переменных.
Я делаю прогу-аудитор блоков. Обрабатываю один единственный блок. Куда сливать результат? Ну придумал какую-то абракадабру и что?
Дальше к этой абракадабре прибавлять и прибавлять еще всякой лабуды?
А так, я могу на основе уникальной переменной, добавляя к ней еще что-нибудь, хранить данные и не думать как их от общей лабуды отделять.
Ну нет в языке AutoIT ни cdr, ни assoc. Список есть, строки есть, принцип формирования переменной есть. Много чего есть такого, что в AutoLISP-e нет. Вот и выкручиваюсь.
Supermax вне форума вставить имя Обратить внимание модератора на это сообщение  
 
Непрочитано 14.12.2009, 23:26
#12
Кулик Алексей aka kpblc
Moderator

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


Опять штатных средств не хватает...
Ну ладно, создавай пользовательский тип переменной и работай с массивом (естественно, что с переменным размером) этих переменных, если так уж не терпится.
__________________

---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума вставить имя Обратить внимание модератора на это сообщение  
Ответ
Вернуться   Форум DWG.RU > Программное обеспечение > Программирование > Перевод имени блока в имя переменной и обратно

Cкидки на VetCAD++
Размещение рекламы
Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск

Быстрый переход

Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
запуск программы из AutoCADа kminas Программирование 19 15.06.2012 13:42
LISP. Имя файла по значениям атрибутов блока. Happy LISP 1 25.11.2008 14:12
Имя блока по его вхождению Mischa Программирование 3 14.10.2007 14:57
Вариация моделей в SCAD - проблемы с РСУ UIII SCAD 2 04.10.2007 13:35

|| Главная || Каталог САПР || Тендеры || Публикации || Объявления || Биржа труда || Download || Галерея ||
|| Библиотека || Кунсткамера || Каталог предприятий || Контакты || Файлообменник || Блоги ||