I have some delegates and a method:
delegate Point Translate(Point p);
delegate Translate Transform(Translate t);
Translate forward = p => new Point(p.X + 1, p.Y);
Question: How can I implement a method like this:
Transform Rotate90 = ??
So that Rotate90
rotates any Translate
function 90 clockwise. So:
Point startPoint = new Point(1, 1);
Point endPoint = (Rotate90(forward))(startPoint);
//desired output: Point(1, 0)
EDIT 1: I'm not going to apply Translate
functions one by one on a point. What I need is to apply some transformed functions ( Translate
function that have been rotated or reflexed) on a point.
WHAT I NEED: How can I write a Rotate90
which if I pass it (p=>new Point(p.X+1, py))
it returns me a function with the same effect as (p=>new Point(pX, pY-1))
.
EDIT 2: Some examples:
Translate forward = p => new Point(p.X + 1, p.Y);
Translate backward = p => new Point(p.X - 1, p.Y);
Translate downward = p => new Point(p.X, p.Y - 1);
Translate runningForward = p => new Point(p.X + 5, p.Y);
Transform Rotate90Cw = ??
Point samplePoint = new Point(1, 1);
Point p1 = (Rotate90Cw(forward))(samplePoint); //must be (1,0)
Point p2 = (Rotate90Cw(backward))(samplePoint); //must be (1,2)
Point p3 = (Rotate90Cw(downward))(samplePoint); //must be (0,1)
Point p4 = (Rotate90Cw(runningForward))(samplePoint); //must be (1,-4)
Point p4 = (Rotate90Cw(Rotate90Cw(forward)))(samplePoint); //must be (0,1)
I need a single
Rotate90Cw
function that can be applied on anyTranslate
function and returns a properTranslate
function. So the effect of applyingRotate90Cw(forward)
on a point would be the same as applyingdownward
on a point. And so on...
I'm not going to make a separate Rotate
function for every case (eg forwardRotated, downwardRotated and ...
It's not clear that you actually want two delegates. It seems that really you want one delegate representing an arbitrary transformation from Point
to Point
- and you can then compose transformations. For example:
delegate Point Transform(Point input);
private static Transform Compose(Transform first, Transform second)
{
return p => second(first(p));
}
Transform forward = p => new Point(p.X + 1, p.Y);
Transform rotate90 = p => new Point(p.Y, -p.X);
Transform forwardThenRotate = Compose(forward, rotate);
EDIT: It looks like what you actually want is a transform (taking in a transform) along the lines of:
We can do that easily:
Transform forward = p => new Point(p.X + 1, p.Y);
Transform rotate90 = p => new Point(-p.Y, p.X);
Point forwardRotatedPoint = rotate90(forward(new Point(0, 0));
Transform forwardRotated = p => new Point(forwardRotatedPoint.X + p.X,
forwardRotatedPoint.Y + p.Y);
As I said elsewhere though, you probably actually want a Vector
type, which has X
and Y
components... then you could have several composable concepts:
I solve it this way (EDITED):
Translate Rotate90Cw(Translate moveFunction)
{
return Rotate(moveFunction, Math.PI / 2.0);
}
Translate Rotate(Translate moveFunction, double angle)
{
Point tempPoint = moveFunction(new Point(0, 0));
double sin = Math.Sin(angle);
double cos = Math.Cos(angle);
return p => new Point(p.X + tempPoint.X * cos + tempPoint.Y * sin,
p.Y - tempPoint.X * sin + tempPoint.Y * cos);
}
Check if it is working:
Rotate90Cw(Rotate90Cw(runningForward))(new Point(1, 1)); //output: (-4,0.9999999)
Rotate90Cw(runningForward)(new Point(1, 1)); //output: (1,-4)
Rotate90Cw(backward)(new Point(1, 1)); //output: (1,2)
Rotate90Cw(downward)(new Point(1, 1)); //output: (0,1)
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.