{"id":5902,"date":"2016-07-13T07:30:08","date_gmt":"2016-07-13T10:30:08","guid":{"rendered":"http:\/\/www.fernandoquadro.com.br\/html\/?p=5902"},"modified":"2016-08-12T14:52:29","modified_gmt":"2016-08-12T17:52:29","slug":"analise-e-visualizacao-de-dados-lidar-parte-2","status":"publish","type":"post","link":"https:\/\/www.fernandoquadro.com.br\/html\/2016\/07\/13\/analise-e-visualizacao-de-dados-lidar-parte-2\/","title":{"rendered":"An\u00e1lise e visualiza\u00e7\u00e3o de dados LiDAR &#8211; Parte 2"},"content":{"rendered":"<p>N\u00f3s vamos carregar os dados LIDAR em uma tabela no PostgreSQL, e depois fazer a an\u00e1lise espacial usando o PostGIS, por isso, vamos precisar de um banco de dados com algumas extens\u00f5es habilitadas.<\/p>\n<ul>\n<li>Crie um novo banco de dados chamado LIDAR<\/li>\n<li>Habilite as extens\u00f5es pointcloud, postgis, e pointcloud_postgis.<\/li>\n<\/ul>\n<p>No PostgreSQL, execute os seguintes comandos:<\/p>\n<pre>CREATE EXTENSION postgis;\r\nCREATE EXTENSION pointcloud;\r\nCREATE EXTENSION pointcloud_postgis;<\/pre>\n<p>Feito isso, agora n\u00f3s podemos carregar os dados.<\/p>\n<p><a href=\"http:\/\/pointcloud.org\/\" target=\"_blank\">PDAL <\/a>, ou &#8220;biblioteca de abstra\u00e7\u00e3o de dados de nuvem de pontos&#8221;, serve para manipular dados de nuvens de pontos espaciais. Ele inclui uma biblioteca de c\u00f3digo (para integra\u00e7\u00e3o em aplica\u00e7\u00f5es) e uma ferramenta de linha de comando. Nuvens de pontos s\u00e3o frequentemente capturados por sensores LIDAR mas tamb\u00e9m podem ser capturados por muitos outros tipos de sensores.<\/p>\n<p>Podemos usar o PDAL atrav\u00e9s da linha de comando para ler alguns metadados do nosso arquivo LAZ:<\/p>\n<pre>pdal info --input 20090429_42122c8225_ld_p23.laz --schema<\/pre>\n<p>O par\u00e2metro &#8211;schema nos mostra informa\u00e7\u00f5es de todas as dimens\u00f5es contidas no arquivo, que neste caso s\u00e3o muitas, veja: <\/p>\n<p>\u201cX\u201d, \u201cY\u201d, \u201cZ\u201d, \u201cIntensity\u201d, \u201cReturnNumber\u201d, \u201cNumberOfReturns\u201d, \u201cScanDirectionFlag\u201d, \u201cEdgeOfFlightLine\u201d, \u201cClassification\u201d, \u201cScanAngleRank\u201d, \u201cUserData\u201d, \u201cPointSourceId\u201d, and \u201cTime\u201d.<\/p>\n<p>N\u00f3s tamb\u00e9m pode ler os metadados do arquivo:<\/p>\n<pre>pdal info --input 20090429_42122c8225_ld_p23.laz --metadata --xml<\/pre>\n<p>O retorno \u00e9 um pouco confuso pois o XML n\u00e3o vem formatado, infelizmente, mas se voc\u00ea ler o <a href=\"http:\/\/workshops.boundlessgeo.com\/tutorial-lidar\/_static\/lidar_metadata.xml\" target=\"_blank\">arquivo formatado<\/a> pode encontrar muita informa\u00e7\u00e3o interessante.<\/p>\n<ul>\n<li>A refer\u00eancia espacial dos dados \u00e9 WGS84 Geogr\u00e1fico<\/li>\n<li>Os limites dos dados s\u00e3o (-122.8874999,42.3125), (- 122.8749998,42.325)<\/li>\n<li>Os dados foram criados utilizando o software &#8220;TerraScan&#8221;<\/li>\n<\/ul>\n<p>N\u00f3s vamos construir um &#8220;pipeline&#8221; para ler nosso arquivo LAZ, e em seguida, escrever os dados em nosso banco de dados.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/www.fernandoquadro.com.br\/html\/wp-content\/uploads\/2016\/07\/pdal_flow.jpg\" alt=\"pdal_flow\" width=\"448\" height=\"66\" class=\"aligncenter size-full wp-image-5973\" srcset=\"https:\/\/www.fernandoquadro.com.br\/html\/wp-content\/uploads\/2016\/07\/pdal_flow.jpg 448w, https:\/\/www.fernandoquadro.com.br\/html\/wp-content\/uploads\/2016\/07\/pdal_flow-300x44.jpg 300w\" sizes=\"auto, (max-width: 448px) 100vw, 448px\" \/><\/p>\n<p>O &#8220;<a href=\"http:\/\/www.pointcloud.org\/pipeline.html\" target=\"_blank\">arquivo de pipeline<\/a>&#8221; \u00e9 um XML que descreve o processamento. Cada processo envolve o processo precedente, resultando numa estrutura &#8220;<em>nesting dolls<\/em>&#8220;, no qual o primeiro processo (o leitor) est\u00e1 no centro e o \u00faltimo (o escritor) est\u00e1 no lado de fora.<\/p>\n<p>Logo abaixo \u00e9 c\u00f3digo do nosso arquivo de pipeline. Note que estamos usando &#8220;EPSG:4326&#8221; como sistema de refer\u00eancia espacial, j\u00e1 que \u00e9 o que aprendemos com os metadados:<\/p>\n<ul>\n<li>Nosso leitor \u00e9 um drivers.las.reader,<\/li>\n<li>Nosso escritor \u00e9 um drivers.pgpointcloud.writer e<\/li>\n<li>No meio, estamos aplicando um filters.chipper<\/li>\n<li>Para mais informa\u00e7\u00f5es sobre filtros de pipeline e leitor\/escritor de PDAL veja a <a href=\"http:\/\/www.pointcloud.org\/stages\/index.html\" target=\"_blank\">documenta\u00e7\u00e3o de refer\u00eancia<\/a>.<\/li>\n<\/ul>\n<p>Copie o c\u00f3digo abaixo para um arquivo de pipeline com o nome de <a href=\"http:\/\/workshops.boundlessgeo.com\/tutorial-lidar\/_static\/laz2pg.xml\" target=\"_blank\">laz2pg.xml<\/a>:<\/p>\n<pre>&lt;?xml&nbsp;version=\"1.0\"&nbsp;encoding=\"utf-8\"?&gt;\r\n&lt;Pipeline&nbsp;version=\"1.0\"&gt;\r\n&nbsp;&nbsp;&lt;Writer&nbsp;type=\"drivers.pgpointcloud.writer\"&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&lt;Option&nbsp;name=\"connection\"&gt;dbname=lidar&nbsp;user=postgres&lt;\/Option&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&lt;Option&nbsp;name=\"table\"&gt;medford&lt;\/Option&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&lt;Option&nbsp;name=\"srid\"&gt;4326&lt;\/Option&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&lt;Filter&nbsp;type=\"filters.chipper\"&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;Option&nbsp;name=\"capacity\"&gt;400&lt;\/Option&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;Filter&nbsp;type=\"filters.cache\"&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;Reader&nbsp;type=\"drivers.las.reader\"&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;Option&nbsp;name=\"filename\"&gt;20090429_42122c8225_ld_p23.laz&lt;\/Option&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;Option&nbsp;name=\"spatialreference\"&gt;EPSG:4326&lt;\/Option&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;\/Reader&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;\/Filter&gt;\r\n&nbsp;&nbsp;&nbsp;&nbsp;&lt;\/Filter&gt;\r\n&nbsp;&nbsp;&lt;\/Writer&gt;\r\n&lt;\/Pipeline&gt;<\/pre>\n<p>Agora estamos prontos para executar o processo de carregamento de dados:<\/p>\n<pre>pdal pipeline laz2pg.xml<\/pre>\n<p>Quando o processo estiver completo, haver\u00e1 uma nova tabela na base de dados:<\/p>\n<pre>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Table&nbsp;\"public.medford\"\r\n&nbsp;Column&nbsp;|&nbsp;&nbsp;&nbsp;&nbsp;Type&nbsp;&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Modifiers\r\n--------+------------+------------------------------------------------------\r\n&nbsp;id&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|&nbsp;integer&nbsp;&nbsp;&nbsp;&nbsp;|&nbsp;not&nbsp;null&nbsp;default&nbsp;nextval('medford_id_seq'::regclass)\r\n&nbsp;pa&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|&nbsp;pcpatch(1)&nbsp;|\r\nIndexes:\r\n&nbsp;&nbsp;&nbsp;&nbsp;\"medford_pkey\"&nbsp;PRIMARY&nbsp;KEY,&nbsp;btree&nbsp;(id)<\/pre>\n<p>Note que o tipo da coluna &#8220;pa&#8221; na base de dados, \u00e9 pcpatch (1). O pcpatch refere-se ao tipo de dados, que \u00e9 um conjunto de nuvem de pontos, agrupados em uma \u00e1rea quadrada, um &#8220;patch&#8221; de dados. O (1) refere-se ao &#8220;formato&#8221; dos pontos dentro do patch: quantas dimens\u00f5es cada ponto tem, e o que essas dimens\u00f5es s\u00e3o. <\/p>\n<pre>SELECT * FROM pointcloud_formats WHERE pcid = 1;<\/pre>\n<p>A informa\u00e7\u00e3o \u00e9 dif\u00edcil de ler no formato de sa\u00edda do PostgreSQL, mas com uma vers\u00e3o formatada pode ser mais f\u00e1cil de entender.<\/p>\n<p>Podemos usar nosso conhecimento do banco e as fun\u00e7\u00f5es da extens\u00e3o pointcloud para saber mais sobre os nossos dados, veja:<\/p>\n<pre>\r\n--&nbsp;How&nbsp;many&nbsp;points&nbsp;are&nbsp;in&nbsp;our&nbsp;cloud?&nbsp;(11418635)\r\nSELECT&nbsp;Sum(PC_NumPoints(pa))\r\nFROM&nbsp;medford;\r\n--&nbsp;What&nbsp;is&nbsp;the&nbsp;average&nbsp;elevation&nbsp;of&nbsp;the&nbsp;first&nbsp;patch?&nbsp;(439.384)\r\nWITH&nbsp;pts&nbsp;AS&nbsp;(\r\n&nbsp;&nbsp;SELECT&nbsp;PC_Explode(pa)&nbsp;AS&nbsp;pt\r\n&nbsp;&nbsp;FROM&nbsp;medford&nbsp;LIMIT&nbsp;1\r\n)\r\nSELECT&nbsp;Avg(PC_Get(pt,'Z'))&nbsp;FROM&nbsp;pts;\r\n--&nbsp;What&nbsp;does&nbsp;the&nbsp;first&nbsp;point&nbsp;look&nbsp;like?\r\nWITH&nbsp;pts&nbsp;AS&nbsp;(\r\n&nbsp;&nbsp;SELECT&nbsp;PC_Explode(pa)&nbsp;AS&nbsp;pt\r\n&nbsp;&nbsp;FROM&nbsp;medford&nbsp;LIMIT&nbsp;1\r\n)\r\nSELECT&nbsp;PC_AsText(pt)&nbsp;FROM&nbsp;pts&nbsp;LIMIT&nbsp;1;\r\n--&nbsp;{\r\n--&nbsp;&nbsp;\"pcid\":1,\r\n--&nbsp;&nbsp;\"pt\":[-122.887,42.3125,439.384,42,1,1,1,0,1,6,181,343,419629,1.14073e+07,0]\r\n--&nbsp;}\r\n--&nbsp;How&nbsp;many&nbsp;patches&nbsp;do&nbsp;we&nbsp;have?&nbsp;(28547)\r\nSELECT&nbsp;Count(*)\r\nFROM&nbsp;medford;\r\n--&nbsp;What&nbsp;is&nbsp;the&nbsp;min\/max&nbsp;elevation&nbsp;in&nbsp;our&nbsp;cloud?&nbsp;(421.20\/467.413)\r\nSELECT\r\n&nbsp;&nbsp;Min(PC_PatchMin(pa,&nbsp;'z'))&nbsp;AS&nbsp;min,\r\n&nbsp;&nbsp;Max(PC_PatchMax(pa,&nbsp;'z'))&nbsp;AS&nbsp;max\r\nFROM&nbsp;medford;\r\n--&nbsp;What&nbsp;does&nbsp;a&nbsp;patch&nbsp;look&nbsp;like&nbsp;as&nbsp;a&nbsp;geometry?\r\nSELECT&nbsp;st_asewkt(pa::geometry)&nbsp;FROM&nbsp;medford&nbsp;LIMIT&nbsp;1;\r\n--&nbsp;SRID=4326;POLYGON((-122.8874998&nbsp;42.3125002,-122.8874998&nbsp;42.312613,\r\n--&nbsp;-122.8874414&nbsp;42.312613,-122.8874414&nbsp;42.3125002,-122.8874998&nbsp;42.3125002))\r\n--&nbsp;What&nbsp;does&nbsp;a&nbsp;point&nbsp;look&nbsp;like&nbsp;as&nbsp;a&nbsp;geometry?\r\nWITH&nbsp;pts&nbsp;AS&nbsp;(\r\n&nbsp;&nbsp;SELECT&nbsp;PC_Explode(pa)&nbsp;AS&nbsp;pt\r\n&nbsp;&nbsp;FROM&nbsp;medford&nbsp;LIMIT&nbsp;1\r\n)\r\nSELECT&nbsp;ST_AsEWKT(pt::geometry)&nbsp;FROM&nbsp;pts&nbsp;LIMIT&nbsp;1;\r\n--&nbsp;SRID=4326;POINT(-122.8874601&nbsp;42.3125002&nbsp;439.384)<\/pre>\n<p>H\u00e1 mais informa\u00e7\u00f5es sobre a extens\u00e3o pointcloud dispon\u00edveis na <a href=\"https:\/\/github.com\/pramsey\/pointcloud\/blob\/master\/README.md\" target=\"_blank\">p\u00e1gina de documenta\u00e7\u00e3o da extens\u00e3o<\/a>.<\/p>\n<p>No pr\u00f3ximo post veremos como disponibilizar os dados LiDAR em um mapa.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>N\u00f3s vamos carregar os dados LIDAR em uma tabela no PostgreSQL, e depois fazer a an\u00e1lise espacial usando o PostGIS, por isso, vamos precisar de um banco de dados com algumas extens\u00f5es habilitadas. Crie um novo banco de dados chamado&#8230; <a class=\"more-link\" href=\"https:\/\/www.fernandoquadro.com.br\/html\/2016\/07\/13\/analise-e-visualizacao-de-dados-lidar-parte-2\/\">Continue Reading &rarr;<\/a><\/p>\n","protected":false},"author":275,"featured_media":5970,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[7,24],"tags":[223,268,277],"class_list":["post-5902","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-geoserver","category-gis","tag-gis","tag-lidar","tag-pdal"],"_links":{"self":[{"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/posts\/5902","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/users\/275"}],"replies":[{"embeddable":true,"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/comments?post=5902"}],"version-history":[{"count":24,"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/posts\/5902\/revisions"}],"predecessor-version":[{"id":6207,"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/posts\/5902\/revisions\/6207"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/media\/5970"}],"wp:attachment":[{"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/media?parent=5902"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/categories?post=5902"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.fernandoquadro.com.br\/html\/wp-json\/wp\/v2\/tags?post=5902"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}