Considering the next things done
Class Point()
{
prop int X
prop int Y
//ByDefault it generates a Random value
Point()
{
GenerateRandom();
}
public void GenerateRandom()
{
//Code for generateRandom
}
}
Class Operations
{
public float Distance(Point A, Point B)
{
//Code for calculating distance
}
///Determinates the distance from i=0 to i=n of the array with a for sentence
public float AcumulatedDistance(Point[] PointsOrdered)
{
float ret=0;
for(i=0;i<n-1;i++)
ret += Distance(PointsOrdered[i], PointsOrdered[i+1]);
return ret;
}
}
What do you have to do to make (in Operations):
public Point[] ShortestPath(int initialIndex, Point[] myPoints)
Where myPoints has a set of points and I consider myPoints[initialindex] my StartPosition. And the array returned is the Points ordered to get the shortest path.
I can't seem to get how to apply Floyd–Warshall niether Dijkstra of if those apply.
Related
I wanted to try c#'s unsafe 'feature' by creating simple structs (Vector, Particle).
SITUATION
I have this 2 structs and want to inject position and velocity vectors into my Particle struct.
As a test I wanted to print out position's X value, but somehow I'm getting random values.
I have the following code here
Vector
public readonly struct Vector
{
public int X { get; }
public int Y { get; }
public Vector(int x, int y)
{
X = x;
Y = y;
}
}
Particle
public unsafe struct Particle
{
private Vector* mPosition;
private Vector* mVelocity;
public Particle(Vector position, Vector velocity = default)
{
mPosition = &position; // here is x 10
mVelocity = &velocity;
}
public int GetPosX()
{
return mPosition->X; // but here not
}
}
Program
public class Program
{
private static void Main(string[] args)
{
var pos = new Vector(10, 5);
var obj = new Particle(pos);
Console.WriteLine(obj.GetPosX()); // prints random value
}
}
PROBLEM
It prints a random value instead of 10.
class Program {
static void Main (string [ ] args) {
unsafe {
Vector pos = new Vector(10, 5);
Particle obj = new Particle(&pos);
// &pos is at position 0xabcdef00 here.
// obj.mPosition has a different value here. It points to a different address? Or am I misunderstanding something
Console.WriteLine(obj.GetPosX( ));
}
}
}
public struct Vector {
public int X;
public int Y;
public Vector (int x, int y) {
X = x;
Y = y;
}
}
public unsafe struct Particle {
private Vector* mPosition;
public Particle (Vector *position) {
mPosition = position; // here is x 10
}
public int GetPosX ( ) {
return mPosition->X; // still 10 here
}
}
This works for me.
Please ... do not ask me why it does. You will notice that I didn't change that much. Just calling Particle with *pos instead of pos. For some reason that fixes the problem. You have to wrap the code with unsafe then and change the constructor for Particle obviously.
I could speculate about why it works, but I'd rather not. Maybe the pointer changes when you pass pos as a parameter for some reason?
You could not take the ref with right value.
Create a variable like int posX = 10;
And you can take the reference with variable. You take the compile time reference and read the runtime reference.
Don't use pointers without fixed. C# stack performance ise very good. You dont need this.
Usually pointers use with linking (C/Cpp dynamic library linking etc). If you have large structs (30 bytes and greater) then you can use the ref parameter tag.
I am working on an assignment with very specific instructions, which, if it is of any intrest, I will post below the code I have created. But, in short, I am to create a BasicShape abstract class, as well as a Circle and Rectangle subclasses. Each subclass has a method for calculating the area of the shape. the area is calculated using member variables. However, in my code below, these member variables are never assigned a value. I am confused as to how to assign it to them, because Circle and Rectangle methods also require arguments to be passed to them. These arguments x, y, r for Circle and w, l for Rectangle are specified in the main program when a new instance of a shape is made, but these values also seem to do nothing, since the output is always 0. What relationship do the arguments passed into the methods have to the member variables? How is it that the member variables should be assigned values when the values are given via arguments set when a Circle or Rectangle instance is called?
Here is my code:
abstract class BasicShape
{
protected double area;
public double getArea()
{
Console.WriteLine("Area: {0}", area);
return area;
}
public virtual void calcArea()
{
}
}
class Circle : BasicShape
{
private int centerX;
private int centerY;
private double radius;
public Circle(int x, int y, double r)
{
calcArea();
}
public int genCenterX()
{
return centerX;
}
public int genCenterY()
{
return centerY;
}
public override void calcArea()
{
area = 3.14159 * radius * radius;
Console.WriteLine("The area of the circle is: {0}", area);
}
}
class Rectangle : BasicShape
{
private int width;
private int length;
public Rectangle(int w, int l)
{
calcArea();
}
public int getWidth()
{
return width;
}
public int getLength()
{
return length;
}
public override void calcArea()
{
area = length * width;
Console.WriteLine("The area of the rectangle is: {0}", area);
}
}
public class TestShapes
{
static void Main(string[] args)
{
Circle circle1 = new Circle(2, 2, 5);
Rectangle rectangle = new Rectangle(6, 7);
Console.ReadLine();
}
}
Here are the instructions for the assignment:
Define a pure abstract base class called BasicShape.
The BasicShape class should have the following members:
Private Member Variable:
area, a double used to hold the shape’s area.
Public Member Methods:
getArea(): This method should return the value in the member variable area.
calcArea(): This method should be a pure virtual method.
Next, define a class named Circle. It should be derived from the BasicShape class. It should have the following members:
Private Member Variable:
centerX, an integer used to hold the x coordinate of the circle’s center.
centerY, an integer used to hold the y coordinate of the circle’s center.
radius, a double used to hold the circle’s radius.
Public Member Methods:
Circle(int x, int y, int r): accepts values for centerX, centerY, and radius. Should call the overridden calcArea
method described below.
genCenterX: returned the value in centerX
genCenterY: returned the value in centerY
calcArea(): calculates the area of the circle (area = 3.14159 * radius * radius) and stored the result in the inherited member area.
Next, define a class named Rectangle. It should be derived from the BasicShape class. It should have the following members:
Private Member Variable:
width, an integer used to hold the width of the rectangle
length, an integer used to hold the length of the rectangle
Public Member Methods:
Rectangle(int w, int l): accepts values for the width and length. Should call the overridden calcArea method described below.
getWidth(): returns the value in width.
getLength(): returns the value in length
calcArea(): calculates the area of the circle (area = length * width) and stored the result in the inherited member area.
After you have created these classes, create a main program that defined a Circle object and a Rectangle object.
Demonstrate that each object properly calculates and reports its area.
You don't assign the values passed from the constructor to your member variables. So when you call calcArea you execute it using the default values for the types int or double (which is zero)
class Circle : BasicShape
{
private int centerX;
private int centerY;
private double radius;
public Circle(int x, int y, double r)
{
radius = r;
// Now you are executing the calcArea using the value passed in
calcArea();
}
....
}
class Rectangle : BasicShape
{
private int width;
private int length;
public Rectangle(int w, int l)
{
width = w;
length = l;
calcArea();
}
....
}
The override of calcArea needs the member variables to be set to something otherwise these member variables are initialized with their default values (zero in both integer and double) and thus the method cannot produce a meaningful result.
I am creating a crossword puzzle generator and seem to have an issue with a simple variable assignment of co-ordinates in the grid system.
I have a very simple structure to hold discrete coordinate values as seen below. I have stripped encapsulation to make it easier to read.
public struct vec2
{
public int x, y;
public vec2(int x, int y)
{
this.x = x;
this.y = y;
}
}
This Vec2 Structure is maintained inside a class to hold word values
public struct WordClass
{
string svalue;
bool flag;
public vec2 position;
public WordClass(string sarg, bool barg)
{
this.svalue = sarg;
this.flag = barg;
position = new vec2(0,0);
}
public string StringVal
{
get { return svalue; }
}
public bool FlagVal
{
get { return flag; }
}
public void DisableWord()
{
if (this.flipflop == false)
{
this.flipflop = true;
}
}
public void SetPos(int xa, int ya)
{
this.position.x = xa;
this.position.y = ya;
}
}
This should basically maintain a list of permanent words with a flag for usage, and a variable position as the system calculates optimal locations for the word.
I have a dynamic linked list of words
List<WordClass> WordList = new List<WordClass>();
and to change the coordinates of a word in the wordlist
//Arbitrary values
WordList[0].SetPos(Position_X, Position_Y);
Now my issue is that when I try to use the position of the word, no matter what I set it too prior, it maintains a default value of 0, 0. I have been scratching my head while doing other functionality, and it's left me wondering if I'm missing something important.
Problem seems to be related to the fact that vec2 is a ValueObject and you're trying to change it. The problematic lines are concretely those two:
this.position.x = xa;
this.position.y = ya;
Why? Because vec2 is a a struct each time you read it you get a temporary copy, then modify that copy, then the copy is thrown away, while you're still reading the original, unmodified one. That's one reason why value objects should be immutable as much as possible, unless you've got a strong reason.
The first step should be to make a proper immutable vec2 structure:
public struct vec2
{
public int x { get; private set; }
public int y { get; private set; }
public vec2(int x, int y)
{
this.x = x;
this.y = y;
}
}
Once you've got that, you need to take care of the modification in the SetPos method. Since the structure is immutable you can no longer read it, but instead each time you need to change it you'll throw the current instance away and create a new one:
public void SetPos(int xa, int ya)
{
this.position = new vec2(xa, ya);
}
This creates a brand-new structure and assings it to the internal field, containing the new values. As this doesn't really attempts to modify the structure, but instead change the structure for a new one it won't be subject to the same subtle bug.
Ok,
It is not possible to store a struct instance inside a struct of the same type. So can anyone help me find a workaround please?
I need to store a vector3 inside a vector3 like this:
public struct Vector3{
float x,y,z;
Vector3 normalized;
}
Obviously, it creates an endless cycle as one would create a new one that creates a new one and so on...
So how would one do that? I would need my normalized to be a Vector3 since it needs to be recognized as such and cannot be any other naming.
Finally, I know this can be achieved with classes but I would not want.
Thanks
Well, a struct is a value type. Declaring a recursive struct would create an infinitely big struct! A workaround would be to declare it as class instead. But here I would simply declare Normalized as a property.
public struct Vector3 {
public Vector3(float x, float y, float z)
{
X = x;
Y = y;
Z = z;
}
public float X { get; private set; }
public float Y { get; private set; }
public float Z { get; private set; }
public float Length {
get { return (float)Math.Sqrt(X * X + Y * Y + Z * Z); }
}
Vector3 Normalized {
get {
float l = Length;
return new Vector3(X / l, Y / l, Z / l);
}
}
}
You cannot store a struct of type X inside a struct of type X. However, you probably don't want to do this anyway, because in general, structs (and classes, for that matter) should only store the data they need to be complete. Instead, you can have a function that builds and returns the 'normalized' version of the struct:
public struct Vector3
{
float x,y,z;
public Vector3 Normalized
{
get
{
... build the normalized struct and return it ...
}
}
}
XNA framework for .net has a really useful Object called vector2 that represents a 2d vector..You can multiply them by ints, floats and other Vector 2s
Eg.
Vector2 bloo = new Vector2(5, 5);
bloo *= 5;
bloo *= someotherVector2;
The only thing is that the X,Y information is stored as floats and in a lot of cases I want to simply store 2d info, or 2d coordinates as ints.
I'd like to make my own struct for this..
Heres what i have..
internal struct Coord
{
public int X { get; private set; }
public int Y { get; private set; }
public Coord(int x,int y)
{
X = x;
Y = y;
}
}
My question is how do I make it so my Coord struct can be multipled by ints or other Coords using * (Not a "Multiply" function call)
You can use operator overloading:
public static Coord operator*(Coord left, int right)
{
return new Coord(left.X * right, left.Y * right);
}
Just put the method into the Coord struct. You can do this with many operators like +,-,/ etc... and also with different parameters.
You need to overload the multiplication operator for you type.
// overload operator *
public static Coord operator *(Coord x, Coord y)
{
// Return a `Coord` that results from multiplying x with y
}
overload multiplication operator:
public static Coord operator* (Coord multiplyThis, Coord withThis) {
Coord result = multiply(multiplyThis, withThis); //...multiply the 2 Coords
return result;
}
public static Coord operator* (Coord multiplyThis, float withThis) {
Coord result = multiply(multiplyThis, withThis); //...multiply the Coord with the float
return result;
}