Извлечение количества элементов с помощью IfcOpenShell в Python - PullRequest
0 голосов
/ 24 мая 2018

Я пытаюсь прочитать самый глубокий уровень величин для объектов в файле ifc, используя IfcOpenShell в Python.Пока у меня есть:

import ifcopenshell

path = r'D:\ifcos_1\slab.ifc'
ifc_file = ifcopenshell.open(path)

geometries = ifc_file.by_type("IfcProduct")

for geometry in geometries:
    if geometry.is_a("IfcSlab"):
        print geometry
        test = geometry.IfcPhysicalQuantity()
        print test

Я изучил определения

Независимо от того, какой тип функции я пытаюсь разместить для test = geometry.X(), я получаюошибка:

File "C:\Python27\lib\site-packages\ifcopenshell\entity_instance.py", line 48, in __getattr__
   "entity instance of type '%s' has no attribute '%s'" % (self.wrapped_data.is_a(), name))
AttributeError: entity instance of type 'IfcSlab' has no attribute 'IfcPhysicalQuantity'

Не знаете, как решить эту проблему, и будем признательны за помощь.

РЕДАКТИРОВАТЬ:

Далееработа, которая получает плиту и дальнейшие ссылки:

for geometry in geometries:
    if geometry.is_a("IfcSlab"):
        print geometry
        definedBy = geometry.IsDefinedBy

        print definedBy[0]

        for each in definedBy:
            test = each.is_a()
            print test

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

РЕДАКТИРОВАНИЕ 2:

Дальнейшая работа с использованием на данный момент стандарта IFC 2x3 с файлом, содержащим информацию о количестве (проверено с помощью необработанных данных).Ниже приведен соответствующий код:

for geometry in geometries:
    if geometry.is_a("IfcSlab"):
        definedBy = geometry.IsDefinedBy

        for line in definedBy:
        test = line.is_a()
        # print test
        if line.is_a() == 'IfcRelDefinesByProperties' or line.is_a() == 'IfcRelDefinesByType':
            step1 = line.RelatingPropertyDefinition
            step2 = step1.is_a()
            print step2

Имеется ошибка, независимо от того, что я ставлю после step1 = line., ни одно из следующего не дает результата:

line.IfcPropertySet
line.IfcElementQuantity
line.RelatingPropertyDefiniton

Вывод изэтот код тем не менее:

IfcPropertySet
IfcPropertySet
IfcPropertySet
IfcPropertySet
IfcPropertySet
IfcPropertySet
IfcPropertySet
IfcPropertySet
IfcPropertySet
IfcPropertySet
IfcElementQuantity
IfcElementQuantity

Это означает, что я могу получить доступ к IfcElementQuantity, но ни один из Атрибутов не работает.Я посмотрел ссылку на схему , но не могу найти правильную.

1 Ответ

0 голосов
/ 24 мая 2018

При реализации этого вы должны позаботиться о том, на какой версии IFC работает ваша библиотека импорта - версия, распространяемая на веб-сайте IfcOpenShell, работает с IFC2X3.Для IFC4 вам, вероятно, потребуется самостоятельно скомпилировать версию.(вы можете проверить свою версию IFC с помощью ifcopenshell.schema_identifier)

Я добавляю ссылки на определение BuildingSMART IFC 4, даже если я говорю о IFC2X3.Отличия от IFC2X3 отмечены красным на веб-странице buildingSMART.И определение IFC4 приятнее для чтения (IMO).

Количества напрямую не связаны как атрибут.Они записываются как наборы свойств и затем связаны с элементом или типом элемента.Поэтому сначала вы должны убедиться, что ваш файл IFC содержит количества, иначе вы их не найдете.Обычно вы начинаете с определенного продукта - ifc_file.by_type('IfcSlab').Вы можете получить доступ к наборам свойств через обратные атрибуты - они обычно устанавливаются библиотекой IFC, они не отображаются напрямую как атрибут в файле.

Я взял файл примера и сократил его примерно до трети(так что это все еще действительный файл IFC2X3):

ISO-10303-21;
HEADER;FILE_DESCRIPTION(('ViewDefinition [Custom, QuantityTakeOffAddOnView, SpaceBoundary2ndLevelAddOnView]','Option [Drawing Scale: 100.000000]','Option [Global Unique Identifiers (GUID): Keep existing]','Option [Elements to export: Visible elements (on all stories)]','Option [Partial Structure Display: Entire Model]','Option [IFC Domain: All]','Option [Structural Function: All Elements]','Option [Convert Grid elements: On]','Option [Convert IFC Annotations and ARCHICAD 2D elements: Off]','Option [Convert 2D symbols of Doors and Windows: Off]','Option [Explode Composite and Complex Profile elements into parts: On]','Option [Export geometries that Participates in Collision Detection only: Off]','Option [Elements in Solid Element Operations: Extruded/revolved]','Option [Elements with junctions: Extruded/revolved without junctions]','Option [Slabs with slanted edge(s): Extruded]','Option [Use legacy geometric methods as in Coordination View 1.0: Off]','Option [IFC Site Geometry: As boundary representation (BRep)]','Option [IFC Site Location: At Project Origin]','Option [Curtain Wall export mode: Container Element]','Option [Railing export mode: Single Element]','Option [Stair export mode: Container Element]','Option [Properties To Export: All properties]','Option [Space containment: On]','Option [IFC Domain For Space Containment: All]','Option [Bounding Box: Off]','Option [Geometry to type objects: Off]','Option [Element Properties: All]','Option [Property Type Element Parameter: On]','Option [Quantity Type Element Parameter: On]','Option [IFC Base Quantities: On]','Option [Window Door Lining and Panel Parameters: On]','Option [IFC Space boundaries: On]','Option [ARCHICAD Zone Categories as IFC Space classification data: On]','Option [Element Classifications: On]'),'2;1');
FILE_NAME('D:\\Side Projects\\Paragraph3\\The database\\IFC Files\\Local tests\\ifcos_1\\slab.ifc','2018-06-13T18:28:40',('Architect'),('Building Designer Office'),'The EXPRESS Data Manager Version 5.02.0100.09 : 26 Sep 2013','IFC file generated by GRAPHISOFT ARCHICAD-64 21.0.0 INT FULL Windows version (IFC2x3 add-on version: 3005 INT FULL).','The authorising person');
FILE_SCHEMA(('IFC2X3'));
ENDSEC;
DATA;
#1= IFCPERSON($,'Undefined',$,$,$,$,$,$);
#7= IFCPERSONANDORGANIZATION(#1,#10,$);
#10= IFCORGANIZATION('GS','GRAPHISOFT','GRAPHISOFT',$,$);
#11= IFCAPPLICATION(#10,'21.0.0','ARCHICAD-64','IFC2x3 add-on version: 3005 INT FULL');
#12= IFCOWNERHISTORY(#7,#11,$,.ADDED.,$,$,$,1528907320);
#13= IFCSIUNIT(*,.LENGTHUNIT.,.MILLI.,.METRE.);
#14= IFCSIUNIT(*,.AREAUNIT.,$,.SQUARE_METRE.);
#16= IFCSIUNIT(*,.PLANEANGLEUNIT.,$,.RADIAN.);
#17= IFCMEASUREWITHUNIT(IFCPLANEANGLEMEASURE(0.0174532925199),#16);
#18= IFCDIMENSIONALEXPONENTS(0,0,0,0,0,0,0);
#19= IFCCONVERSIONBASEDUNIT(#18,.PLANEANGLEUNIT.,'DEGREE',#17);
#29= IFCUNITASSIGNMENT((#13,#14,#19));
#31= IFCDIRECTION((1.,0.,0.));
#35= IFCDIRECTION((0.,0.,1.));
#37= IFCCARTESIANPOINT((0.,0.,0.));
#39= IFCAXIS2PLACEMENT3D(#37,#35,#31);
#40= IFCDIRECTION((0.,1.));
#42= IFCGEOMETRICREPRESENTATIONCONTEXT($,'Model',3,1.00000000000E-5,#39,#40);
#45= IFCPROJECT('344O7vICcwH8qAEnwJDjSU',#12,'Project',$,$,$,$,(#42),#29);
#59= IFCLOCALPLACEMENT($,#39);
#62= IFCSITE('20FpTZCqJy2vhVJYtjuIce',#12,'Site',$,$,#59,$,$,.ELEMENT.,(47,33,34,948800),(19,3,17,204400),0.,$,$);
#68= IFCRELAGGREGATES('0Du7$nzQXCktKlPUTLFSAT',#12,$,$,#45,(#62));
#74= IFCQUANTITYLENGTH('GrossPerimeter',$,$,0.);
#76= IFCQUANTITYAREA('GrossArea',$,$,0.);
#77= IFCELEMENTQUANTITY('2GNZepdf73fvGc$0W6rozj',#12,'BaseQuantities',$,'ARCHICAD BIM Base Quantities',(#74,#76));
#82= IFCRELDEFINESBYPROPERTIES('2Hm9JvZjohDNSD2kdxZI3b',#12,$,$,(#62),#77);
#93= IFCLOCALPLACEMENT(#59,#39);
#95= IFCBUILDING('00tMo7QcxqWdIGvc4sMN2A',#12,'Building',$,$,#93,$,$,.ELEMENT.,$,$,$);
#97= IFCRELAGGREGATES('2b_h_mYcGArd6glJG2Fmbt',#12,$,$,#62,(#95));
#101= IFCQUANTITYAREA('GrossFloorArea',$,$,0.);
#102= IFCELEMENTQUANTITY('1kQMlmT0rD35a9E43iKTas',#12,'BaseQuantities',$,'ARCHICAD BIM Base Quantities',(#101));
#104= IFCRELDEFINESBYPROPERTIES('0L87OdSD3DqSTjSRlAciZL',#12,$,$,(#95),#102);
#115= IFCLOCALPLACEMENT(#93,#39);
#117= IFCBUILDINGSTOREY('1oZ0wPs_PE8ANCPg3bIs4j',#12,'Ground Floor',$,$,#115,$,$,.ELEMENT.,0.);
#119= IFCRELAGGREGATES('118jwqMnuwK1xuf97w7fU5',#12,$,$,#95,(#117));
#180= IFCSLAB('3W29Drc$H6CxK3FGIxjJNl',#12,'SLA - 001',$,$,$,$,'E0089375-9BF4-4633-B503-3D04BBB535EF',.FLOOR.);
#195= IFCRELCONTAINEDINSPATIALSTRUCTURE('04ldtj6cp2dME6CiP80Bzh',#12,$,$,(#180),#117);
#326= IFCPROPERTYSINGLEVALUE('Fragility rating',$,IFCLABEL('0'),$);
#327= IFCPROPERTYSINGLEVALUE('Tile dimensions',$,IFCLABEL('Undefined'),$);
#328= IFCPROPERTYSINGLEVALUE('Anti-static Surface',$,IFCBOOLEAN(.F.),$);
#329= IFCPROPERTYSINGLEVALUE('Non-skid Surface',$,IFCBOOLEAN(.F.),$);
#330= IFCPROPERTYSET('0LYX8AqOOS9ft8M4aJYEYa',#12,'FLOORINGS',$,(#326,#327,#328,#329));
#332= IFCRELDEFINESBYPROPERTIES('1G6WWCSQGg0PdTnW7hwMrM',#12,$,$,(#180),#330);
#335= IFCPROPERTYSINGLEVALUE('Renovation Status',$,IFCLABEL('Existing'),$);
#336= IFCPROPERTYSET('0cR6wsk2QWcLKPchA8mF3u',#12,'AC_Pset_RenovationAndPhasing',$,(#335));
#338= IFCRELDEFINESBYPROPERTIES('3nYD8KGPhoBw5okmj1JjsA',#12,$,$,(#180),#336);
#341= IFCQUANTITYLENGTH('Width',$,$,300.);
#342= IFCQUANTITYLENGTH('Perimeter',$,$,22000.);
#343= IFCQUANTITYAREA('GrossArea',$,$,28.);
#344= IFCQUANTITYAREA('NetArea',$,$,28.);
#345= IFCQUANTITYVOLUME('GrossVolume',$,$,8.4);
#346= IFCQUANTITYVOLUME('NetVolume',$,$,8.4);
#347= IFCELEMENTQUANTITY('1RfXJewSc7OCIaD$L2ZoXT',#12,'BaseQuantities',$,'ARCHICAD BIM Base Quantities',(#341,#342,#343,#344,#345,#346));
#349= IFCRELDEFINESBYPROPERTIES('085uLttAQRllG3nL_YikZ8',#12,$,$,(#180),#347);
#375= IFCQUANTITYVOLUME('Gross Volume of the Slab',$,$,8.4);
#376= IFCQUANTITYVOLUME('Gross Volume of the Slab with Holes',$,$,8.4);
#377= IFCQUANTITYLENGTH('Holes Perimeter',$,$,0.);
#378= IFCQUANTITYAREA('Holes Surface Area',$,$,0.);
#379= IFCQUANTITYLENGTH('Perimeter',$,$,22000.);
#381= IFCQUANTITYAREA('Top Surface Area',$,$,28.);
#382= IFCELEMENTQUANTITY('0DuZ12CVtssgcIQPaQ$1sp',#12,'ArchiCADQuantities',$,'ARCHICAD BIM Quantities',(#375,#376,#377,#378,#379,#381));
#384= IFCRELDEFINESBYPROPERTIES('0KgGv0Y8Fc2jg8BCPhxnM5',#12,$,$,(#180),#382);
#393= IFCSLABTYPE('0K1otpnkQcEpOBXPxnZ3dB',#12,'Timber - Floor 300',$,$,(#396),$,'14072DF3-C6E6-A63B-360B-859EF18C39CB',$,.FLOOR.);
#395= IFCRELDEFINESBYTYPE('353egCMRpZtJd$CDCoSsCb',#12,$,$,(#180),#393);
#352= IFCQUANTITYAREA('Area',$,$,28.);
#353= IFCQUANTITYLENGTH('Height',$,$,300.);
#354= IFCQUANTITYVOLUME('Net Volume',$,$,8.4);
#396= IFCELEMENTQUANTITY('1Zyxf4r7NogSp4V7ORMpET',#12,'ArchiCADQuantities',$,'ARCHICAD BIM Quantities',(#352,#353,#354));
ENDSEC;
END-ISO-10303-21;

Это плита с прикрепленным измерением площади.Он должен иметь обратный атрибут IsDefinedBy.В IFC2X3 это указывает на список объектов IfcRelDefinesByProperties и IfcRelDefinesByType .С IFC4 IfcRelDefinesByType будет помещен в обратный атрибут IsTypedBy.

Каждый IfcRelDefinesByProperties указывает на свойство, установленное в их атрибуте RelatingPropertyDefinition.Существуют различные типы наборов свойств, вы хотите, чтобы он имел тип IfcElementQuantity при поиске физических величин.Вам нужно будет проверить во время выполнения, какой тип вы используете в данный момент, итерируя список отношений свойств.

У набора количества есть список IfcPhysicalQuantities , прикрепленный в атрибуте Quantities.Это могут быть простые величины или сложные величины, которые состоят из нескольких простых величин.Для простых количеств есть определенные подтипы для площади, количества или веса.Опять же, вам придется проверять во время выполнения конкретный тип.

У самой области количества есть имя и описание, чтобы дать дополнительный контекст (не наш, но, возможно, в реальном мире).Атрибут значения назван в честь типа количества, поэтому IfcQuantityArea имеет атрибут AreaValue.Также представляет интерес атрибут Unit, который является ссылкой на единицу значения.Если он не установлен (как в нашем примере), вам нужно искать назначенные единицы в объекте IfcProject.

К сожалению, это может быть не все.Если объект (здесь наш IfcSlab) имеет назначенный тип объекта, к этому типу также могут быть прикреплены наборы свойств (в этом случае я изменил файл примера).Сущность вашего типа не имеет обратного атрибута, но имеет прямой атрибут HasProperties.Если он установлен, вы можете открывать присоединенные свойства через него.

Подводя итог, вам, вероятно, понадобится несколько циклов:

  1. Для каждого объекта получите наборы свойств
  2. Для каждого набора свойств проверьте, задано ли это количество
  3. Для каждого набора количеств просмотрите количества

и, возможно, повторите этот поиск, если объект имеет определенный пользователем тип.

Следующий код должен делать именно это (написано на моей машине с python 3.5.4 и ifcopenshell со схемой IFC2X3)):

  1. Получить все слябы из файла (есть только один)
  2. Просмотрите все объекты в обратном атрибуте IsDefinedBy - это могут быть IfcRelDefinesByProperties или IFcRelDefinesByType.
  3. Получить наборы свойств от объекта
  4. Проверить,данный набор свойств равен IfcElementQuantity и приступает к печати количественных показателей, если он есть.
import ifcopenshell
def print_quantities(property_definition):
  if 'IfcElementQuantity' == property_definition.is_a():
    for quantity in property_definition.Quantities:
      if 'IfcQuantityArea' == quantity.is_a():
        print('Area value: ' + str(quantity.AreaValue))
      if 'IfcQuantityVolume' == quantity.is_a():
        print('Volume value: ' + str(quantity.VolumeValue))
      if 'IfcQuantityLength' == quantity.is_a():
        print('Length value: ' + str(quantity.LengthValue))

ifc_file = ifcopenshell.open('slab.ifc')
products = ifc_file.by_type('IfcSlab')
for product in products:
  if product.IsDefinedBy:
    definitions = product.IsDefinedBy
    for definition in definitions:
      #In IFC2X3 this could be property or type
      #in IFC4 type is in inverse attribute IsTypedBy
      if 'IfcRelDefinesByProperties' == definition.is_a():
        property_definition = definition.RelatingPropertyDefinition
        print_quantities(property_definition)
      if 'IfcRelDefinesByType' == definition.is_a():
        type = definition.RelatingType
        if type.HasPropertySets:
          for property_definition in type.HasPropertySets:
            print_quantities(property_definition)

Для примера это приводит к:

Length value: 300.0
Length value: 22000.0
Area value: 28.0
Area value: 28.0
Volume value: 8.4
Volume value: 8.4
Volume value: 8.4
Volume value: 8.4
Length value: 0.0
Area value: 0.0
Length value: 22000.0
Area value: 28.0
Area value: 28.0
Length value: 300.0
Volume value: 8.4
...