Выбор многоугольника ArcSDE в ArcGIS Desktop с помощью ArcPy?

15

Я продолжаю думать, что я должен что-то упустить, но в ArcGIS 10, похоже, нет инструмента для выбора объектов (в частности, полигонов) из слоя в точке (X, Y) с помощью ArcPy. Параметры для такого инструмента будут просто именем слоя и местоположением XY.

В настоящее время я обхожу это путем создания точечного класса объектов, содержащего точку, и выполнения над ней SelectLayerByLocation. Однако, когда класс объектов полигонов находится в Oracle (доступ к которому осуществляется через ArcSDE 9.x) и содержит 3,5 миллиона полигонов, время, необходимое для выбора, может составить более 5 минут, когда я думаю, что секунда или две (с меньшим количеством кода) будут более подходящий. Класс пространственных объектов имеет пространственный индекс, и я попытался использовать arcpy.env.extent (который SelectLayerByLocation игнорирует), чтобы ограничить доступ к географической области, но производительность остается очень низкой.

Есть ли более быстрый способ сделать это с помощью ArcGIS Desktop 10 и ArcPy?

PolyGeo
источник
Теперь есть решение этой проблемы на forum.arcgis.com/threads/…, и я отредактирую эту информацию здесь позже сегодня - большое спасибо Джейсону Шейреру и Крису Снайдеру
PolyGeo
2
В качестве примечания к этому вы можете найти среду, которая поддерживается инструментом, внизу справочной страницы инструмента. SelectByLocation учитывает только текущую рабочую область и выходную систему координат. help.arcgis.com/en/arcgisdesktop/10.0/help/index.html#//…
blord-castillo

Ответы:

9

Другим подходом к этому будет использование инструмента Пространственное соединение. Используйте точку в качестве входного векторного слоя, как указано выше, и слой многоугольника в качестве объектов идентификации.
В отличие от SelectLayerByLocation, SpatialJoin поддерживает среду экстентов .

targetlayer = layername
joinlayer=arcpy.PointGeometry(arcpy.Point(x, y))
fieldmappings = arcpy.FieldMappings()
fieldmappings.addTable(targetlayer)
arcpy.SpatialJoin_analysis(targetlayer, joinlayer, outputlayer, "JOIN_ONE_TO_MANY", "KEEP_COMMON", fieldmappings)

JOIN_ONE_TO_MANY может показаться нелогичным, но, поскольку у вас есть только одна функция объединения, основная функция этого параметра - отключить агрегацию и правила объединения. KEEP_COMMON позаботится о том, чтобы ваш вывод ограничивался только полигоном, который пересекает вашу точку. Сопоставления полей будут ограничивать выходные атрибуты только формой и атрибутами слоя многоугольника; значение по умолчанию также включает атрибуты точечного слоя.

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

blord-Castillo
источник
Большое спасибо за этот код, который содержал пару методов, которые я не пробовал. Ранее я пробовал SpatialJoin (чтобы можно было уважать среду геообработки), но это тестирование, а также тестирование вашей техники только что оставили мне время отклика 4-5 минут по сравнению с 10-12 секундами для способа Крис Снайдер привел меня к.
PolyGeo
Вы тоже пробовали технику Криса Снайдера с SpatialJoin? Я думаю, что основная причина, по которой буферная техника настолько быстра, заключается в том, что она использует копию класса polygon в памяти. Я думаю, выбор по местоположению должен быть быстрее, чем пространственное соединение, но я не уверен.
blord-castillo
Завершено не использованием бита in_memory. Это было уже настолько ускорено, что я оставил это в запасе. Я думаю, что ключевым моментом была установка экстента, чтобы получить один / несколько полигонов (из 3,5 миллионов), которые мне нужно было проверить, X и Y быстро скопировали в локальную файловую базу геоданных. Я думаю, что выполнение этой части до SpatialJoin приведет к тому же / аналогичному улучшению производительности.
PolyGeo
1

Я только что понял что-то ...

Если вы используете это для реализации Сервиса геообработки, вы можете также реализовать Сервис объектов с вашим полигональным слоем и использовать операцию Запрос в сервисе объектов.

Вы можете использовать простое расположение XY с операцией запроса сервисов объектов, а также управлять выходными атрибутами, включая форму.

У вас могут быть ограничения на количество объектов класса полигонов, которые вы можете предоставить, но если вы уже делаете его доступным для сервиса геообработки, вы также сможете создать сервис пространственных объектов.

blord-Castillo
источник
Это полезная мысль для удовлетворения других требований, но в этом случае клиентское приложение очень простое и не зависит от меня, поэтому я могу предоставить только услугу геообработки.
PolyGeo
Я подумал, что может быть ограничение на использование чего-либо, кроме сервиса геообработки :) По иронии судьбы, я считаю, что сервис объектов - это гораздо более простой путь для реализации и поддержки. Это также может объяснить, почему нужная вам функциональность недоступна; Вы уже можете сделать это на каждом уровне приложения. Убедитесь, что вы отправили запрос в ESRI, чтобы реализовать его в качестве инструмента в следующей версии.
blord-castillo
1

Этот ответ пришел со старых дискуссионных форумов ArcGIS .

Спасибо Джейсону Шейреру за более краткий код:

SelectLayerByLocation(in_layer=arcpy.PointGeometry(arcpy.Point(x, y)), select_features="mylayer") 

И особенно Крису Снайдеру за совет по производительности:

Более быстрым обходным путем может быть небольшая буферизация вашей точки, а затем использование экстента буфера в качестве экстента анализа для создания копии in_memory (инструмент CopyFeatures) ваших данных SDE, а затем выполнение SelectByLocation для меньшего и локального набора данных in_memory. Таким образом, вы как бы заставляете инструмент SelectByLocation соблюдать среду экстента анализа, чего он обычно не делает. Кстати: все функции, которые перекрываются с экстентом анализа, будут скопированы с помощью инструмента CopyFeatures. Я уверен, что инструмент SelectByLocation и методы курсоров учитывают степень анализа ...

PolyGeo
источник