Polygon comparison between layers - vector

I'm trying to compare specific polygons between layers (different years), to see if there has been any change to the area. Eg[2021 & 2019]2019 & 2021 In this example (from left to right), A would decrease by the amount that is outside of the layer, as well as the amount that B is now taking instead. C would also increase in area.
The difference, symmetrical difference, union, and intersection tools all find areas outside the total bounding box of the layer, but cannot find changes to polygons within the layer.
My desired output is a change (either % or absolute) in area from each layer to a master layer (the latest year).
(Some polygons get split and/or renamed, however I suspect this is a small enough cohort that it can be addressed manually.)
Edit: Currently trying "Detect Dataset Changes", but the polygons don't exactly 100% overlap, the 0.00000001% changes in the border mess it up and mark every polygon as changed. Posted as new question: Is there a tolerance setting I can use with "detect dataset changes" tool?

Related

Rendering highly granular and "zoomed out" data

There was a gif on the internet where someone used some sort of CAD and drew multiple vector pictures in it. On the first frame they zoom-in on a tiny dot, revealing there a whole new different vector picture just on a different scale, and then they proceed to zoom-in further on another tiny dot, revealing another detailed picture, repeating several times. here is the link to the gif
Or another similar example: imagine you have a time-series with a granularity of a millisecond per sample and you zoom out to reveal years-worth of data.
My questions are: how such a fine-detailed data, in the end, gets rendered, when a huge amount of data ends up getting aliased into a single pixel.
Do you have to go through the whole dataset to render that pixel (i.e. in case of time-series: go through million records to just average them out into 1 line or in case of CAD render whole vector picture and blur it into tiny dot), or there are certain level-of-detail optimizations that can be applied so that you don't have to do this?
If so, how do they work and where one can learn about it?
This is a very well known problem in games development. In the following I am assuming you are using a scene graph, a node-based tree of objects.
Typical solutions involve a mix of these techniques:
Level Of Detail (LOD): multiple resolutions of the same model, which are shown or hidden so that only one is "visible" at any time. When to hide and show is usually determined by the distance between camera and object, but you could also include the scale of the object as a factor. Modern 3d/CAD software will sometimes offer you automatic "simplification" of models, which can be used as the low res LOD models.
At the lowest level, you could even just use the object's bounding
box. Checking whether a bounding box is in view is only around 1-7 point checks depending on how you check. And you can utilise object parenting for transitive bounding boxes.
Clipping: if a polygon is not rendered in the view port at all, no need to render it. In the GIF you posted, when the camera zooms in on a new scene, what is left from the larger model is a single polygon in the background.
Re-scaling of world coordinates: as you zoom in, the coordinates for vertices become sub-zero floating point numbers. Given you want all coordinates as precise as possible and given modern CPUs can only handle floats with 64 bits precision (and often use only 32 for better performance), it's a good idea to reset the scaling of the visible objects. What I mean by that is that as your camera zooms in to say 1/1000 of the previous view, you can scale up the bigger objects by a factor of 1000, and at the same time adjust the camera position and focal length. Any newly attached small model would use its original scale, thus preserving its precision.
This transition would be invisible to the viewer, but allows you to stay within well-defined 3d coordinates while being able to zoom in infinitely.
On a higher level: As you zoom into something and the camera gets closer to an object, it appears as if the world grows bigger relative to the view. While normally the camera space is moving and the world gets multiplied by the camera's matrix, the same effect can be achieved by changing the world coordinates instead of the camera.
First, you can use caching. With tiles, like it's done in cartography. You'll still need to go over all the points, but after that you'll be able zoom-in/zoom-out quite rapidly.
But if you don't have extra memory for cache (not so much actually, much less than the data itself), or don't have time to go over all the points you can use probabilistic approach.
It can be as simple as peeking only every other point (or every 10th point or whatever suits you). It yields decent results for some data. Again in cartography it works quite well for shorelines, but not so well for houses or administrative boarders - anything with a lot of straight lines.
Or you can take a more hardcore probabilistic approach: randomly peek some points, and if, for example, there're 100 data points that hit pixel one and only 50 hit pixel two, then you can more or less safely assume that if you'll continue to peek points still pixel one will be twice as likely to be hit that pixel two. So you can just give up and draw pixel one with a twice more heavy color.
Also consider how much data you can and want to put in a pixel. If you'll draw a pixel in black and white, then there're only 256 variants of color. And you don't need to be more precise. Or if you're going to draw a pixel in full color then you still need to ask yourself: will anyone notice the difference between something like rgb(123,12,54) and rgb(123,11,54)?

MariaDB spatial query to determine proportion of overlap

Background: I have two tables containing geometries (polygons and multipolygons). One table contains large polygons that touch but do not overlap (they are actually administrative boundaries). The other contains smaller polygons (in this case, they are parcels of land).
In most cases, each smaller polygon from the second table will be wholly contained within one of the larger polygons from the first table. This is simple enough to determine with spatial queries (ST_WITHIN). Some, however, will overlap two (or, theoretically, more) admin area polygons.
The question is, for those smaller polygons which overlap two large ones, how can I tell which it is most in?
This image illustrates the situation. Land parcel A is wholly within Leftshire, and B is wholly within Rightshire. This is a simple ST_WITHIN spatial query. I can determine that C overlaps both Leftshire and Rightshire as ST_WITHIN will be false but ST_OVERLAP will be true for both of them. But how can I determine that C is more in Leftshire than it is in Rightshire?
For reference, I am using MariaDB 5.5.64. If the problem is more easily solved using a different version (or even using a different DB), that would be an acceptable fallback, but I would ideally like to solve it using the tools I have to hand if possible.
[Edit: One simple solution would be to check which larger area the centroid of the smaller area falls into. This would work perfectly for rectangles, as in the example. However, it will not be reliable where the shapes are more complex, and I need this to work even for complex multipolygons as neither administrative areas nor land parcels are reliably simple in real life!]

Finding a quantity of anything between two points in space

I'm currently working towards a 3D model of this, but I thought I would start with 2D. Basically, I have a grid of longitude and latitude with NO2 concentrations across it. What I want to produce, at least for now, is a total amount of Nitrogen Dioxide between two points. Like so:
2DGrid
Basically, These two points are at different lats and lons and as I stated I want to find the amount of something between them. The tricky thing to me is that the model data I'm working with is gridded so I need to be able to account for the amount of something along a line at the lat and lons at which that line cuts through said grid.
Another approach, and maybe a better one for my purposes, could be visualized like this:3DGrid
Ultimately, I'd like to be able to create a program (within any language honestly) that could find the amount of "something" between two points in a 3D grid. If you would like specfics, the bottom altitude is the surface, the top grid is the top of the atmosphere. The bottom point is a measurement device looking at the sun during a certain time of day (and therefore having a certain zenith and azimuth angle). I want to find the NO2 between that measurement device and the "top of the atmosphere" which in my grid is just the top altitude level (of which there are 25).
I'm rather new to coding, stack exchange, and even the subject matter I'm working with so the sparse code I've made might end up creating more clutter than purely asking the question and seeing what methods/code you might suggest?
Hopefully my question is beneficial!
Best,
Taylor
To traverse all touched cells, you can use Amanatides-Woo algorithm. It is suitable both for 2D and for 3D case.
Implementation clues
To account for quantity used from every cell, you can apply some model. For example, calculate path length inside cell (as difference of enter and exit coordinates) and divide by normalizing factor to get cell weight (for example, byCellSize*Sqrt(3) for 3D case as diagonal length).

Determine minimum number of "invisible squares" to cover all markers on a map?

I have a map full of markers corresponding to GPS coordinates, represented as a PostgreSQL + PostGIS database table using "geography" type for the GPS column.
Imagine, if you will, one semi-transparent square on top of each of these points corresponding to 1x1 mile, based from the centre, often intersecting with each other.
I'm trying to determine the minimum number of such "squares" and their GPS coordinates, so that they "cover" all of the markers with a minimum of 25 meters to the nearest border.
If it makes it any easier, the positions of these "squares" don't have to match the positions of any of the markers.
The purpose of this is to attempt to cut down the number of API requests to a "houses for sale" service significantly, since most of the positions are close to each other and the API takes a 1x1 mile square "bounding box" as the input for each call. It would be insanely wasteful to call the API many times for basically the same area when maybe 1 or 2 times would do it if I can first figure out where these imaginary "squares" go.
I get the feeling that this is considered a "known, common and solved" problem, but so far, I've not been able to figure out how to do it.
Sorry, but it seems like you have no idea what you are doing and are just being rude, both here and at PostGIS irc-channel.
You give no information about your api.
What is creating your maps?
Is it a wms-service or what?
What most people would do is setting up a mapservice with a tile cache. Then the mapservice will pich the tiles needed for each house you want to show ( or multiple houses).
The tiles will be prepared o will be created on the fly. But they will be cached for next time.
So, I think you should read up on things like
MapServer
Mapnik
MapCache
Mapproxy
GeoServer
That is not a complete list, but might give you some ideas about what it is that you want

Calculate a dynamic iteration value when zooming into a Mandelbrot

I'm trying to figure out how to automatically adjust the maximum iteration value when moving around in the Mandelbrot fractal.
All examples I've found uses a constant of 1000 or less but that's not enough when zooming into the fractal set.
Is there a way to determine the number of max_iterations based on for example where you are in the Mandelbrot space (x_start,x_end,y_start,y_end)?
One method I tried was to repetitively pre-process a small area in the region of the Mset boundary with increasing iterations until the percentage change in status from one repetition to the next was small. The problem was, that would vary in different places on the current map, since the "depth" varies across it. How to find the right place to do it? By logging the "deepest" boundary area during the previous generation (that will still be within the next zoom area).
But my best strategy was to avoid iterating wherever possible:
Away from the boundary of the Mset, areas of equal depth can be "contoured" and then filled with that depth. It was not an easy algorithm. Basically I followed a raster scan but when I detected a boundary of iteration change (examining all the neighbours to ensure I wasn't close the the edge of the Mset), I would switch to a curve-stitching method to iterate around a contour back to where it started (obviously not recalculating spots I already did), and then make a second pass filling in the raster lines within the countour with the iteration level. It was fraught with leaks but eventually I cracked it.
Within the Mset, I followed the same approach, because the very last thing you want to do is to plough across vast areas and hit the iteration limit.
The difficult area is close the the boundary, where the iteration results can't be related to smooth contours with the neighbours. The contour stitching method won't work here, since there is only ever 1 pixel of a particular depth.
Using the contour method also will have faults to the lower or Mset sides of this region, but since this area looks chaotic until you zoom deeper, I lived with that.
So having said all that, I simply set the iteration depth as high as I can tolerate, but perhaps you can combine my first paragraph with the area-filling techniques.
BTW colouring the region adjacent to the Mset looks terrible when an animated smooth playback of the zoom is attempted. For that reason I coloured this area in a grey scale, by comparing with neighbours. If there was too much difference, I coloured to 0x808080 at first, then adapted that depending on the predominance of the neighbours' depth. All requiring fine tuning!

Resources