Building a Conditional JPQL Statement - spring-boot

Here is a JPQL statement that I currently have defining a repository method in Spring Boot.
#Query("SELECT s FROM Station s WHERE s.latitude <= (:latitude + .5) AND"
+ "s.latitude >= (:latitude - .5) AND "
+ "s.longitude <= (:longitude + .5) AND "
+ "s.longitude >= (:longitude - .5)")
List<Station> findAllNear(#Param("latitude") double latitude,
#Param("longitude") double longitude);
The premise behind this statement is I want to find any and all stations within a 1 degree by 1 degree box around the given coordinates if any. I am not concerned with actual distance, as the results will be refined by my business logic elsewhere.
The problem I have is this will not work well around the 180 degree longitude (nor around the poles, but I am not as concerned about that as the likelihood at this juncture of us querying that far north is slim)
Specifically, if someone were to ask for a location at or around 180 degrees longitude, it would not find stations at -179.5 or closer.
How should I adjust the JPQL to handle these cases? Is the only approach to also test for +- 360 degrees on the longitude? Is it possible to cluster groups in this way using JPQL?
A && B && ((C && D) || (E && F) || (G && H))
The JPQL Language documentation says that parentheses are allowed in an expression, but it lists AND and OR as between expression operators. Can AND and OR exist within parentheses?
Also, is there an easier way to do this?

Yes, JPQL allows in between expressions within parentheses, so an argument of the form
A && B && ((C && D) || (E && F) || (G && H))
is valid. Changing my select statement to:
#Query("SELECT s FROM Station s WHERE (s.latitude <= (:latitude + .5) AND"
+ "s.latitude >= (:latitude - .5)) AND "
+ "(s.longitude <= (:longitude + .5) AND s.longitude >= (:longitude - .5)) OR "
+ "(s.longitude <= (:longitude + 360.5) AND s.longitude >= (:longitude +359.5)) OR "
+ "(s.longitude <= (:longitude - 359.5) AND s.longitude >= (:longitude - 360.5)))")
List<Station> findAllNear(#Param("latitude") double latitude,
#Param("longitude") double longitude);
Accomplished what I set out to do.

Related

GLSL optimization: check if variable is within range

In my shader I have variable b and need to determine within which range it lies and from that assign the right value to variable a. I ended up with a lot of if statements:
float a = const1;
if (b >= 2.0 && b < 4.0) {
a = const2;
} else if (b >= 4.0 && b < 6.0) {
a = const3;
} else if (b >= 6.0 && b < 8.0) {
a = const4;
} else if (b >= 8.0) {
a = const5;
}
My question is could this lead to performance issues (branching) and how can I optimize it? I've looked at the step and smoothstep functions but haven't figured out a good way to accomplish this.
To solve the problem depicted and avoid branching the usual techniques is to find a series of math functions, one for each condition, that evaluate to 0 for all the conditions except the one the variable satisfies. We can use these functions as gains to build a sum that evaluates to the right value each time.
In this case the conditions are simple intervals, so using the step functions we could write:
x in [a,b] as step(a,x)*step(x,b) (notice the inversion of x and b to get x<=b)
Or
x in [a,b[ as step(a,x)-step(x,b) as explained in this other post: GLSL point inside box test
Using this technique we obtain:
float a = (step(x,2.0)-((step(2.0,x)*step(x,2.0)))*const1 +
(step(2.0,x)-step(4.0,x))*const2 +
(step(4.0,x)-step(6.0,x))*const3 +
(step(6.0,x)-step(8.0,x))*const4 +
step(8.0,x)*const5
This works for general disjoint intervals, but in the case of a step or staircase function as in this question, we can simplify it as:
float a = const1 + step(2.0,x)*(const2-const1) +
step(4.0,x)*(const3-const2) +
step(6.0,x)*(const4-const3) +
step(8.0,x)*(const5-const4)
We could also use a 'bool conversion to float' as means to express our conditions, so as an example step(8.0,x)*(const5-const4) is equivalent to float(x>=8.0)*(const5-const4)
You can avoid branching by creating kind of a lookup table:
float table[5] = {const1, const2, const3, const4, const5};
float a = table[int(clamp(b, 0.0, 8.0) / 2)];
But the performance will depend on whether the lookup table will have to be created in every shader or if it's some kind of uniform... As always, measure first...
It turned out Jaa-cs answere wasn't viable for me as I'm targeting WebGL which doesn't allow variables as indexes (unless it's a loop index). His solution might work great for other OpenGL implementations though.
I came up with this solution using mix and step functions:
//Outside of main function:
uniform vec3 constArray[5]; // Values are sent in to shader
//Inside main function:
float a = constArray[0];
a = mix(a, constArray[1], step(2.0, b));
a = mix(a, constArray[2], step(4.0, b));
a = mix(a, constArray[3], step(6.0, b));
a = mix(a, constArray[4], step(8.0, b));
But after some testing it didn't give any visible performance boost. I finally ended up with this solution:
float a = constArray[0];
if (b >= 2.0)
a = constArray[1];
if (b >= 4.0)
a = constArray[2];
if (b >= 6.0)
a = constArray[3];
if (b >= 8.0)
a = constArray[4];
Which is both compact and easily readable. In my case both these alternatives and my original code performed equally, but at least here are some options to try out.

Using conditions to find imaginary and real part

I have used Solve to find the solution of an equation in Mathematica (The reason I am posting here is that no one could answer my question in mathematica stack.)The solution is called s and it is a function of two variables called v and ro. I want to find imaginary and real part of s and I want to use the information that v and ro are real and they are in the below interval:
$ 0.02 < ro < 1 ,
40
The code I used is as below:
ClearAll["Global`*"]
d = 1; l = 100; k = 0.001; kk = 0.001;ke = 0.0014;dd = 0.5 ; dr = 0.06; dc = 1000; p = Sqrt[8 (ro l /2 - 1)]/l^2;
m = (4 dr + ke^2 (d + dd)/2) (-k^2 + kk^2) (1 - l ro/2) (d - dd)/4 -
I v p k l (4 dr + ke^2 (d + dd)/2)/4 - v^2 ke^2/4 + I v k dr l p/4;
xr = 0.06/n;
tr = d/n;
dp = (x (v I kk/2 (4 dr + ke^2 (d + dd)/2) - I v kk ke^2 (d - dd)/8 - dr l p k kk (d - dd)/4) + y ((xr I kk (ro - 1/l) (4 dr + ke^2 (d + dd)/2)) - I v kk tr ke^2 (1/l - ro/2) + I dr xr 4 kk (1/l - ro/2)))/m;
a = -I v k dp/4 - I xr y kk p/2 + l ke^2 dp p (d + dd)/8 + (-d + dd)/4 k kk x + dr l p dp;
aa = -v I kk dp/4 + xr I y k p/2 - tr y ke^2 (1/l - ro/2) - (d - dd) x kk^2/4 + ke^2 x (d - dd)/8;
ca = CoefficientArrays[{x (s + ke^2 (d + dd)/2) +
dp (v I kk - l (d - dd) k p kk/2) + y (tr ro ke^2) - (d -
dd) ((-kk^2 + k^2) aa - 2 k kk a)/(4 dr + ke^2 (d + dd)/2) == 0, y (s + dc ke^2) + n x == 0}, {x, y}];
mat = Normal[ca];
matt = Last#mat;
sha = Solve[Det[matt] == 0, s];
shaa = Assuming[v < 100 && v > 40 && ro < 1 && ro > 0.03,Simplify[%]];
reals = Re[shaa];
ims = Im[shaa];
Solve[reals == 0, ro]
but it gives no answer. Could anyone help? I really appreciate any solution to this problem.
I run your code down to this point
mat = Normal[ca]
and look at the result.
There are lots of very tiny floating point coefficients, so small that I suspect most of them are just floating point noise now. Mathematica thinks 0.1 is only known to 1 significant digit of precision and your mat result is perhaps nothing more than zero correct digits now.
I continue down to this point
sha = Solve[Det[matt] == 0, s]
If you look at the value of sha you will see it is s->stuff and I don't think that is at all what you think it is. Mathematica returns "rules" from Solve, not just expressions.
If I change that line to
sha = s/.Solve[Det[matt] == 0, s]
then I am guessing that is closer to what you are imagining you want.
I continue to
shaa = Assuming[40<v<100 && .03<ro<1, Simplify[sha]];
reals = Re[shaa]
And I instead use, because you are assuming v and ro to be Real and because ComplexExpand has often been very helpful in getting Re to provide desired results,
reals=Re[ComplexExpand[shaa]]
and I click on Show ALL to see the full expanded value of that. That is about 32 large screens full of your expression.
In that are hundreds of
Arg[-1. + 50. ro]
and if I understand your intention I believe all those simplify to 0. If that is correct then
reals=reals/.Arg[-1. + 50. ro]->0
reduces the size of reals down to about 20 large screen fulls.
But there are still hundreds of examples of Sqrt[(-1.+50. ro)^2] and ((-1.+50. ro)^2)^(1/4) making up your reals. Unfortunately I'm expecting your enormous expression is too large and will take too long for Simplify with assumptions to be able to be practically effective.
Perhaps additional replacements to coax it into dramatically simplifying your reals without making any mistakes about Real versus Complex, but you have to be extremely careful with such things because it is very common for users to make mistakes when dealing with complex numbers and roots and powers and functions and end up with an incorrect result, might get your problem down to the point where it might be feasible for
Solve[reals == 0, ro]
to give you a meaningful answer.
This should give you some ideas of what you need to think carefully about and work on.

Simple collsion not working to the left or top

This should be a very easy question, basically I have two squares, and I'm trying to see if they overlap. So far I've figured out the right and bottom collisions, but I can't figure out collisions from the left and top. Here's my code:
if (e.getX() >= player.getX() && e.getX() <= player.getX() + Entity.SIZE && e.getY() >= player.getY() && e.getY() <= player.getY() + Entity.SIZE) {
return true;
Let e be the entity that I'm checking and Entity.SIZE be the size for both the squares. What am I doing wrong?
I would suggest just making the player and every entity have a bounding rectangle using java's Rectangle class. You can do easy operations like:
if(e.boundingBox.intersects(player.boundingBox)){...}
where each entity has something like:
private Rectangle boundingBox;
Silly me, I forgot to check for the size on the x and y axis when above or next to a rectangle. Here's the new code:
e.getX() + Entity.SIZE >= player.getX() && e.getX() <= player.getX() + Entity.SIZE && e.getY() + Entity.SIZE >= player.getY() && e.getY() <= player.getY() + Entity.SIZE

Can I easily skip pixels in Bresenham's line algorithm?

I have a program which is using Bresenham's line algorithm to scan pixels in a line. This is reading pixels rather than writing them, and in my particular case, reading them is costly.
I can however determine that some spans of pixels do not need to be read. It looks something like this:
Normal scan of all pixels:
*start
\
\
\
\
\
*end
Scan without reading all pixels:
*start
\
\
- At this point I know I can skip (for example) the next 100 pixels
in the loop. Crucially, I can't know this until I reach the gap.
\
*end
The gap in the middle is much quicker because I can just iterate over the pixels without reading them.
However, can I modify the loop in any way to just jump directly forward 100 pixels within the loop, calculating directly the required values 100 steps ahead in the line algorithm?
Bresenhams middlepoint algorithm calculates 'distance' of point from a theoretical line going from (ax,ay)->(bx,by) by summing up digital differences delta_x = (by-ay), delta_y = (ax-bx).
Thus, if one want's to skip 7 pixels, one has to add accum += 7*delta_x; then dividing by delta_y one can check how many pixels should have been moved in y-direction and taking a remainder accum = accum % delta_y one should be able to continue at proper position.
The nice thing is that the algorithm is originated from the necessity of avoiding a division...
Disclaimer: whatever told may need to be adjusted by half delta.
Your main loop looks essentially something like:
while (cnt > 0) // cnt is 1 + the biggest of abs(x2-x1) and abs(y2-y1)
{
ReadOrWritePixel(x, y);
k += n; // n is the smallest of abs(x2-x1) and abs(y2-y1)
if (k < m) // m is the biggest of abs(x2-x1) and abs(y2-y1)
{
// continuing a horizontal/vertical segment
x += dx2; // dx2 = sgn(x2-x1) or 0
y += dy2; // dy2 = sgn(y2-y1) or 0
}
else
{
// beginning a new horizontal/vertical segment
k -= m;
x += dx1; // dx1 = sgn(x2-x1)
y += dy1; // dy1 = sgn(y2-y1)
}
cnt--;
}
So, skipping some q pixels is equivalent to the following adjustments (unless I made a mistake somewhere):
cntnew = cntold - q
knew = (kold + n * q) % m
xnew = xold + ((kold + n * q) / m) * dx1 + (q - ((kold + n * q) / m)) * dx2
ynew = yold + ((kold + n * q) / m) * dy1 + (q - ((kold + n * q) / m)) * dy2
Note that / and % are integer division and modulo operators.

mirror bits in char, limited operators +,<<,& no loops allowed, C language

Preparing for exam and got stuck at this question:
Allowed operators are <<,+,& no loops allowed and minimum temp variables.
Write a function in C, that gets 4-bit number (char) and returns mirrored (relative to center) bits.
Example: given b4,b3,b2,b1 return b1,b2,b3,b4
O_o thanks!
it might be not clear, but general language tools are allowed ('==',if,>,< etc..)
This is not possible given the constraints of only the operators <<, +, & and no other constructs besides return.
To move b3 from the 3rd position to the 2nd position, you will need a way to shift to the right which requires something like >> or /. Of the operators provided, none can be used with b3 to set the 2nd or 1st bit position.
if you can use if statements and the assignment operator =, it is possible. You can then write a messy solution such as
char flip(char c)
{
char f;
f = (c & 1) << 3 + (c & 2) << 1;
if (c & 4)
f = f + 2;
if (c & 8)
f = f + 1;
return f;
}
A more ugly but shorter one liner if you can use the similar to if ? operator.
char flip(char c)
{
return (c & 1) << 3 + (c & 2) << 1 + ((c & 4) ? 2 : 0) + ((c & 8) ? 1 : 0);
}

Resources