I am trying to figure out whether given those constraints regular 2D packing problem can be simplified. You have n regular s-sided polygons for s between 3 and 12. All of them have the same side length. We need to minimise the area of bounding square.
I would think that having all of the regular with same side length the packing can be easier since some configurations will always fit perfectly next to each other. Though I am not sure whether this property is of any use since local minimum might not translate to global minimum.
From your description, the polygons are regular polygons with all sides having the same length
This means that every polygon edges can connect to form a circle which can fit into a sub-square of size of 2r^2 perfectly
So an easy solution is to fit N polygons aligned in a square of size >= N * 2r^2, this is not an optimal solution, but works perfectly when you only have squares.
Here is an illustration that explains it:
First, knowing that all polygon sides have length of m
The polygon fits perfectly into a circle of ratio r
That circle fits perfectly into a square of size 2r^2
So we finally merge the fitting squares into one big square by tiling them in a matrix of M x M squares, where M * M >= N
Related
Given a set of n points (a_1, b_1), (a_2, b_2), ..., (a_n, b_n). Need to find the minimum x such that three axis parallel squares each of length x together covers all of the points.
I can find the rectangle with smallest area enclosing all the points. Can this rectangle be used somehow? Or any hint on how to approach this problem?
I think, it is enough to consider two cases:
When each square touches some edge of smallest-area rectangle.
When two squares are located at opposite corners of smallest-area rectangle while third one lies inside (does not touch any edge of smallest-area rectangle).
In first case we could fix corner of one square at one of 4 rectangle's corners, then fix corners of other two squares somewhere at two opposite (to chosen corner) edges of the rectangle (n possible positions for each one), then for each point determine optimal square where it belongs and minimum x.
In second case try two opposite pairs of rectangle corners for "outer" squares, then fix one of corners of the "inner" square at all n*n positions determined by all x and y point coordinates, then for each point determine optimal square where it belongs and minimum x.
Time complexity would be O(n3).
The answer of #EvgenyKluev seems to go in the right direction, but there's a couple of subtleties that I'd like to address.
Since I didn't see a restriction for x being integer, you might want to go with binary search on x to guide your algorithm, and find suitable terminating conditions when the range still available for x is small enough (you would do binary search for integer x as well, but there you don't need a terminating condition).
The placement of a square in one corner of the rectangle (something that you will have to do, somewhat straightforward to prove) limits your search space for the placement of the other two squares: let A be the set of points covered by the corner-aligned first square, and let S be the set of all points. Take S-A and find the enclosing rectangle of that set of points. Placing the remaining two squares at opposite corners of the enclosing rectangle of S-A will always be a solution (only one pair of opposite corners might fit), if one exists.
Thus, one algorithm could - very high level - go like this
binary search for x on [0,N]:
find R(S), the enclosing rectangle of S
for each corner C of R(S):
align one square at C, let the points covered by that square be A
find R(S-A)
do two squares aligned at opposite corners of R(S-A) cover S-A?
As for the binary search, I can't really say how fast that will converge to a range that allows only one alignment of squares, at which point you can directly calculate the value x - I expect that with arbitrary precision, you can make that arbitrarily bad. Each iteration takes O(n log n) for sorting the points in both cardinal directions.
Is there any algorithm that can approximate the given polygon with n non overlapping rectangles that gives the maximum coverage? By maximum coverage I mean, the sum of the rectangle areas are maximized. Rectangles are not necessarily equal sized.
The polygons I am dealing are convex. If exact solution is hard/expensive to find (which I am expecting it to be), simple good heuristics are welcome too.
Edit I always thought of approximating the polygon with rectangles inside polygon, but solutions with rectangles not totally inside polygons are also fine. If that is the case, maximization of the area becomes minimization of the area.
Edit 2 I forgot to mention that these rectangles are orthogonal rectangles, i.e. aligned with axises.
One approach would be to create a (in the general case rectangular) bounding box for your polygon. Calculate the difference between the area of the bounding box and the area of the polygon. If the difference is small enough, you're done, if not, continue ...
Divide the box into 4 equal-sized rectangles, 2x2. Figure out which of these rectangles is entirely inside the polygon. Calculate the difference between the total area of the rectangles inside the polygon and of the polygon. If the difference is small enough you're done, if not continue ...
Divide each of the 4 rectangles into 4 sub-rectangles ... if at any stage you find that a rectangle is either fully inside or fully outside your polygon you can remove it from the list of rectangles to subdivide at the next iteration.
In other words, use a quadtree to divide the space containing your polygon and develop it to the extent necessary to meet your accuracy criteria.
Create a queue of polygons, Q, to be processed
Add the initial polygon to Q
Remove a polygon P from Q
Find the longest side A of P
Rotate P so that A is on the X-axis
If P is a triangle, split it with a perpendicular line in the centre of A:
Add the two halves G and H to Q and goto 3
(Now, P has 4 or more sides)
If X and/or Y are acute:
10 . Take the next longest side of P, A, and goto 5
11 . Project a red rectangle up from A. Find the 2 points where it intersects P, B and C:
12 . Choose the longer(B) and finalise the green rectangle
13 . Add the remaining figures (D, E and F) to Q
14 . Goto 3
I realize this is a really old question but I recently stumbled across a similar problem where I had to try to approximate a polygon with rectangles. Using some of the ideas presented here and elsewhere, I started with an inscribed rectangle and generated rectangles around the inscribed rectangle to provide the general shape of the polygon.
This approach works well for convex polygons and reasonable well for some concave polygons - especially if you take an iterative approach (e.g. feed output rectangles as inputs to another iteration).
For extremely concave shapes, you might consider breaking up the polygon into convex hulls and then applying the technique I described above. The Bayazit implementation looks very promising.
In case anyone is interested, I have posted my implementation using inscribed rectangles here:
https://github.com/pborissow/Poly2Rect
A first idea, maybe others can improve on it.
place a squaresomewhere inside the polygon, as far as possible away from any edges.
iteratively
1.) grow it,
2.) move it and turn it to maximize its distance from edges. until you can't grow it any more
start from the beginning, while considering edges of placed rectangles as edges of the polygon.
How many squares of size a×a can be packed into a circle of radius R?
I don't need a solution. I just need some kind of a starting idea.
I apologise for writing such a long answer. My approach is to start with a theoretical maximum and a guaranteed minimum. When you approach the problem, you can use these values to determine how good any algorithm you use is. If you can think of a better minimum then you can use that instead.
We can define an upper limit for the problem by simply using the area of the circle
Upper Limit = floor( (PI * (r pow 2)) / (L * L) )
Where L is the width or height of the squares you are packing and r is the radius of the circle you are packing the squares into. We are sure this is an upper limit because a) we must have a discrete number of boxes and b) we cannot take up more space than the area of the circle. (A formal proof would work somewhere along the lines of assume we had one more box than this, then the sum of the area of the boxes would be greater than the area of the circle).
So with an upper limit in hand, we can now take any solution that exists for all circles and call it a minimum solution.
So, let's consider a solution that exists for all circles by taking a look at the largest square we can fit inside the circle.
The largest square you can fit inside the circle has 4 points on the perimiter, and has a width and length of sqrt(2) * radius (by using pythagoras' theorem and using the radius for the length of the shorter edges)
So the first thing we note is that if sqrt(2) * radius is less than the dimension of your squares, then you cannot fit any squares in the circle, because afterall, this is the largest square you can fit.
Now we can do a straightforward computation to divide this large square into a regular grid of squares using the L you specified, which will give us at least one solution to the problem. So you have a grid of sqaures inside this maximum square. The number of squares you can fit into one row of this this grid is
floor((sqrt(2) * radius)/ L)
And so this minimum solution asserts that you can have at least
Lower Limit = floor((sqrt(2) * radius)/ L) pow 2
number of squares inside the circle.
So in case you got lost, all I did was take the largest square I could fit inside the circle and then pack as many squares as possible into a regular grid inside that, to give me at least one solution.
If you get an answer at 0 for this stage then you cannot fit any squares inside the circle.
Now armed with a theoreitical maximum and an absolute minimum, you can start trying any sort of heuristic algorithm you like for packing squares. A simple algorithm would be to just split the circle up into rows and fit as many sqaures as you can into each row. You can then take this minimum as a guideline to ensure that you came up with a better solution. If you want to spend more processing power looking for a better solution, you use the theoretical as a guideline for how close you are to the theoretical best.
And if you care about this, you could work out what the maximum and minimum theoretical percentage of cover the minimum algorithm I idenfied gives you. The largest square always covers a fixed ratio (pi/4 or about 78.5% of the internal area of the circle I think). So the maximum theoretical minimum is 78.5% cover. And the minimum non-trivial (ie. non zero) theoretical minimum is when you can only fit 1 square inside the largest square, which happens when the squares you are packing are 1 larger than half the width and height of the largest square you can fit in the circle. Basically you take up just over 25% of the inner square with 1 packed square, which means you get an approximate cover of about 20%
Rasterise the circle using something like the midpoint circle algorithm. The number of filled pixels is the number of squares you can fit in the circle. Of course, since you're not actually filling the pixels, just counting them, this should take time proportional to the circumference of the circle, not its area.
You'll have to pick the radius for rasterisation carefully, so that you only count pixels that are strictly inside the circle.
Edit: This may not be exactly correct, as it's possible that applying a sub-pixel offset to the grid could change the result. I'll leave the answer here as it may provide a useful starting point for an exact solution.
You can pack as many squares as you like into a circle. If you doubt this statement, draw a large circle on a piece of paper, then draw a square with side length 10^(-18)m inside it, repeat. When you get near to the boundary of the circle, start drawing squares with side length of 10^(-21)m.
So your first step must be to refine your question and state your problem more accurately.
Just a shot in the dark after a few minutes of thought...
What if you worked with half the circle and doubled it at the end. I would start with a grid of squares the length of the diameter and the width of the radius, essentially blanketing the semi-circle. Then check all 4 corners of each square and make sure their coordinates are within the radius of the circle. This would of course require that you plot the circle and squares on some sort of coordinate system or grid.
I hope this makes sense... It's in my head and it seems a bit difficult to articulate :)
EDIT:
After drawing it out, I think this method would work with a little tweaking. I would line up the squares along the diameter, but slide the first one down until it fits. Set that one in place and start lining up squares next to it until they no longer fit. Move out to the edge of this line of squares and repeat the same steps until your rows of squares reach the radius.
I'm writing a Gaussian blur with variable radius (standard deviation), i.e. each pixel of the image is convolved using a different kernel. The standard techniques to compute Gaussian blur don't work here: FFT, axis-separation, repeated box-blur—they all assume that the kernel is the same for the whole image.
Now, I'm trying to approximate it using the following scheme:
Approximate the Gaussian kernel K(x,y) with a piecewise constant function f(x,y) defined by a set N of axis-aligned rectangles Rk and coefficients αk as:
f(x,y) = ∑k=1N αk·χRk(x,y)
Let g(x,y) be our image, then
∬ℝ2 K(x,y)·g(x,y) dxdy ≈
∬ℝ2 f(x,y)·g(x,y) dxdy = ∑k=1N αk·∬Rkg(x,y) dxdy
The integral on the RHS is a simple integral over a rectangle, and as such can be computed in constant time by precomputing the partial sums for the whole image.
The resulting algorithm runs in O(W·H·N) where W and H are the dimensions of the image and N is (AFAIK) inverse proportional to the error of the the approximation.
The remaining part is to find a good approximation function f(x,y). How to find the optimal approximation to the Gaussian when given either the number of rectangles N (minimizing the error) or given the error (minimizing the number of rectangles)?
Given the locations and size of the rectangles, it should be fairly easy to work out your coefficients, so the real problem is working out where to put the rectangles.
Since you are approximating a Gaussian, it seems at least reasonable to restrict our attention to rectangles whose centre coincides with the centre of the Gaussian, so we actually have only a 1-dimensional problem - working out the sizes of a nested set of rectangles which I presume are either squares or are similar to the Gaussian if you have an aspect ratio other than unity.
This can be solved via dynamic programming. Suppose that you work from the outside into the middle. At stage N you have worked out an n x k table that gives you the best possible approximation error coming from 1,2...N rings of outer pixels for up 1,2,..k different rectangles, and the size of the innermost rectangle responsible for that best error. To work out stage N+1 you consider every possible size for what will be an innermost rectangle so far, contributing x rings of pixels to the outer area. You work out the alpha for that rectangle that gives the best fit for the pixels in the new ring and the rings outside it not left to outer rectangles. Using the values in the table already calculated you know the best possible error you will get when you leave up to k outer rectangles to cover those areas, so you can work out the best total error contributed from what is now N+1 rings of pixels. This allows you to fill in the table entries for N+1 outer pixels. When you have worked your way into the middle of the area you will be able to work out the optimal solution for the whole area.
I have an image of which this is a small cut-out:
As you can see it are white pixels on a black background. We can draw imaginary lines between these pixels (or better, points). With these lines we can enclose areas.
How can I find the largest convex black area in this image that doesn't contain a white pixel in it?
Here is a small hand-drawn example of what I mean by the largest convex black area:
P.S.: The image is not noise, it represents the primes below 10000000 ordered horizontally.
Trying to find maximum convex area is a difficult task to do. Wouldn't you just be fine with finding rectangles with maximum area? This problem is much easier and can be solved in O(n) - linear time in number of pixels. The algorithm follows.
Say you want to find largest rectangle of free (white) pixels (Sorry, I have images with different colors - white is equivalent to your black, grey is equivalent to your white).
You can do this very efficiently by two pass linear O(n) time algorithm (n being number of pixels):
1) in a first pass, go by columns, from bottom to top, and for each pixel, denote the number of consecutive pixels available up to this one:
repeat, until:
2) in a second pass, go by rows, read current_number. For each number k keep track of the sums of consecutive numbers that were >= k (i.e. potential rectangles of height k). Close the sums (potential rectangles) for k > current_number and look if the sum (~ rectangle area) is greater than the current maximum - if yes, update the maximum. At the end of each line, close all opened potential rectangles (for all k).
This way you will obtain all maximum rectangles. It is not the same as maximum convex area of course, but probably would give you some hints (some heuristics) on where to look for maximum convex areas.
I'll sketch a correct, poly-time algorithm. Undoubtedly there are data-structural improvements to be made, but I believe that a better understanding of this problem in particular will be required to search very large datasets (or, perhaps, an ad-hoc upper bound on the dimensions of the box containing the polygon).
The main loop consists of guessing the lowest point p in the largest convex polygon (breaking ties in favor of the leftmost point) and then computing the largest convex polygon that can be with p and points q such that (q.y > p.y) || (q.y == p.y && q.x > p.x).
The dynamic program relies on the same geometric facts as Graham's scan. Assume without loss of generality that p = (0, 0) and sort the points q in order of the counterclockwise angle they make with the x-axis (compare two points by considering the sign of their dot product). Let the points in sorted order be q1, …, qn. Let q0 = p. For each 0 ≤ i < j ≤ n, we're going to compute the largest convex polygon on points q0, a subset of q1, …, qi - 1, qi, and qj.
The base cases where i = 0 are easy, since the only “polygon” is the zero-area segment q0qj. Inductively, to compute the (i, j) entry, we're going to try, for all 0 ≤ k ≤ i, extending the (k, i) polygon with (i, j). When can we do this? In the first place, the triangle q0qiqj must not contain other points. The other condition is that the angle qkqiqj had better not be a right turn (once again, check the sign of the appropriate dot product).
At the end, return the largest polygon found. Why does this work? It's not hard to prove that convex polygons have the optimal substructure required by the dynamic program and that the program considers exactly those polygons satisfying Graham's characterization of convexity.
You could try treating the pixels as vertices and performing Delaunay triangulation of the pointset. Then you would need to find the largest set of connected triangles that does not create a concave shape and does not have any internal vertices.
If I understand your problem correctly, it's an instance of Connected Component Labeling. You can start for example at: http://en.wikipedia.org/wiki/Connected-component_labeling
I thought of an approach to solve this problem:
Out of the set of all points generate all possible 3-point-subsets. This is a set of all the triangles in your space. From this set remove all triangles that contain another point and you obtain the set of all empty triangles.
For each of the empty triangles you would then grow it to its maximum size. That is, for every point outside the rectangle you would insert it between the two closest points of the polygon and check if there are points within this new triangle. If not, you will remember that point and the area it adds. For every new point you want to add that one that maximizes the added area. When no more point can be added the maximum convex polygon has been constructed. Record the area for each polygon and remember the one with the largest area.
Crucial to the performance of this algorithm is your ability to determine a) whether a point lies within a triangle and b) whether the polygon remains convex after adding a certain point.
I think you can reduce b) to be a problem of a) and then you only need to find the most efficient method to determine whether a point is within a triangle. The reduction of the search space can be achieved as follows: Take a triangle and increase all edges to infinite length in both directions. This separates the area outside the triangle into 6 subregions. Good for us is that only 3 of those subregions can contain points that would adhere to the convexity constraint. Thus for each point that you test you need to determine if its in a convex-expanding subregion, which again is the question of whether it's in a certain triangle.
The whole polygon as it evolves and approaches the shape of a circle will have smaller and smaller regions that still allow convex expansion. A point once in a concave region will not become part of the convex-expanding region again so you can quickly reduce the number of points you'll have to consider for expansion. Additionally while testing points for expansion you can further cut down the list of possible points. If a point is tested false, then it is in the concave subregion of another point and thus all other points in the concave subregion of the tested points need not be considered as they're also in the concave subregion of the inner point. You should be able to cut down to a list of possible points very quickly.
Still you need to do this for every empty triangle of course.
Unfortunately I can't guarantee that by adding always the maximum new region your polygon becomes the maximum polygon possible.