C# 定义点类
【日志】
【时间紧急的朋友下面的文字可以不用看】
2019/4/3
C#这门语言,在大二上学期学过,说是学过,其实很心虚。因为当时完全是听得云里雾里的。也许是因为自己的编程经历太少了,然后在大二下老师让用C# 编程,自己就……
前几天看到自己的艾EZ发了几篇博客,所以我也手痒了。自己以前也在这上面得到过许多帮助,所以写这篇博客来帮助那些需要帮助的朋友,并纪念我用一天时间搞明白怎么来定义一个点类。这是小白本人写的第一篇博客,大神勿喷!!!
2020/4/14
今天回首看这篇博客,我哭辽,当时还是太嫩,下面做点修饰。本想尽量保留一下原有的内容,可是觉得当时还是太傻,就大换血了。
2020/6/11
添加了一些函数,诸如相加,相见,数乘,求距离等。
2020/6/12
添加了构造函数3,求其到另一个点的坐标方位角等。现在它已经要依附于角类了。
2020/6/13
添加了构造函数4,与drawing 里面的PointF 联系了起来
2020/6/25
改进了构造函数2,
2020/6/28 今天我发现了一件特尴尬的事情,我定义的这个Point
,和 System.Drawing.Point
重名了,真的是…当时年少,一无所知。但是找到解决方法了,如果想使用系统的Point
的话,就用 System.Drawing.Point
即可,想使用自己定义的Point
的话,直接Point
即可!!
1. 点类使用介绍
1.构造函数1,将一串数据传到一个 Point 中
public Point(double x = 0, double y = 0, double z = 0, string name = "0")
2.构造函数2,重载 Point函数,将一个字符串数组传到 Point 中
//mod 1带名字,0 不带名字,默认不带名字
public Point(string[] sArry)
3.打印出点
pt.show();
4.点数组重心化,最后一个点存重心坐标
Point[] pt=Point.ZXH(pt1);
5.求pt1 和 pt2 之间的欧式距离
double dis=pt1.Dis(pt2);
6.重载运算符
+ - * \
7.找出一个点数组中最接近(0,0)的下标
public static int find_Close0(Point[] p)
8.判断 其与p2 哪个和(0,0)更接近
public bool IsClose0(Point p2)
9.得到此点到p2 的坐标方位角
public Angle getAn(Point p2)
10.构造函数3,已知基点,边长,方位角求另一个点
public Point(Point p1, double s, Angle a)
11.构造函数4 将 PointF 转化为 Point, 需要using System.Drawing;
public Point(PointF p1)
2. 源码
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Drawing;//与PointF 联系起来了
namespace Handy_Calculator //这里改成和您的namespace 名字一样即可
{
public class Point
{//Define fields
public string name;
public double x; //coordinate
public double y;
public double z;
public string Name
{ get { return name; } set { name = value; } }
public double X
{ get { return x; } set { x = value; } }
public double Y
{ get { return y; } set { y = value; } }
public double Z
{ get { return z; } set { z = value; } }
//The constructor
public Point(double x = 0, double y = 0, double z = 0, string name = "0")
{//构造函数1,将一串数据传到一个 Point 中
this.name = name;
this.x = x;
this.y = y;
this.z = z;
}
public Point(string[] sArry,int mod=0)
{//构造函数2,重载 Point函数,将一个字符串数组传到 Point 中
//mod 1带名字,0 不带名字,默认不带名字
int n = sArry.Length;
if (mod == 1)
{
this.name = sArry[0];
this.x = double.Parse(sArry[1]);
this.y = double.Parse(sArry[2]);
if (n < 4)
this.z = 0;
else
this.z = double.Parse(sArry[3]);
}
else
{
this.x = double.Parse(sArry[0]);
this.y = double.Parse(sArry[1]);
if (n < 3)
this.z = 0;
else
this.z = double.Parse(sArry[2]);
}
}
public Point(Point p1, double s, Angle a)
{//构造函数3 已知基点,边长,方位角,求另一个点
this.x = p1.x + s * a.cos;
this.y = p1.y + s * a.sin;
this.z = p1.z;
this.name = "0";
}
public Point(PointF p1)
{//构造函数4 将 PointF 转化为 Point, 需要using System.Drawing;
this.x = p1.X;
this.y = p1.Y;
this.z = 0;
this.name = "0";
}
public Point Add(Point p2)
{//两点相加
return new Point(this.x + p2.x, this.y + p2.y, this.z + p2.z);
}
public Point Sub(Point p2)
{//两点相减
return new Point(this.x - p2.x, this.y - p2.y, this.z - p2.z);
}
public Point Mut(double d)
{//点与数相乘
return new Point(this.x * d, this.y * d, this.z * d);
}
public Point Div(double d)
{//点与数相除
return new Point(this.x / d, this.y / d, this.z / d);
}
public double Dis(Point p2)
{//求距离
return Math.Sqrt((this.x - p2.x) * (this.x - p2.x) + (this.y - p2.y) *
(this.y - p2.y) + (this.z - p2.z) * (this.z - p2.z));
}
public Angle getAn(Point p2)
{//以此点为基点,得到其到另一个点的坐标方位角
return new Angle(arctan(this.x - p2.x, this.y - p2.y));
}
public bool IsClose0(Point p2)
{//判断 其与p2 哪个和(0,0)更接近
if (Math.Abs(this.x) < Math.Abs(p2.x) &&
Math.Abs(this.y) < Math.Abs(p2.y) &&
Math.Abs(this.x) < Math.Abs(p2.x))
return true;
else
return false;
}
public static int find_Close0(Point[] p)
{//找出一个点数组中最接近(0,0)的下标
int n = p.Length, index = 0;
for (int i = 1; i < n; i++)
{
if (p[i].IsClose0(p[index]))
index = i;
}
return index;
}
/*此函数用于求象限角
* 返回的是弧度,取值范围为[0,2*pi)
*/
public static double arctan(double dx, double dy)
{
double angle = 0;
if (dx == 0)
{
if (dy > 0) angle = Math.PI * 0.5;
else angle = Math.PI * 1.5;
return angle;
}
angle = Math.Atan2(Math.Abs(dy), Math.Abs(dx));
if (dx < 0)
{
if (dy < 0) angle = Math.PI + angle;
else angle = Math.PI - angle;
}
else if (dy < 0) angle = 2 * Math.PI - angle;
return angle;
}
public void show()
{//打印出点坐标
Console.WriteLine("X {0:f3}, Y {1:f3}, Z {2:f3}, Name {3}", this.x, this.y, this.z, this.name);
}
public double Dis2To0()
{//到原点距离的平方
return this.x * this.x + this.y * this.y + this.z * this.z;
}
public static Point[] ZXH(Point[] pt)
{//坐标重心化,最后一个点存重心坐标
int n = pt.Length;
Point[] po = new Point[n + 1];
double x0 = 0, y0 = 0, z0 = 0;
for (int i = 0; i < n; i++)
{
x0 += pt[i].x;
y0 += pt[i].y;
z0 += pt[i].z;
}
x0 /= n; y0 /= n; z0 /= n;
for (int i = 0; i < n; i++)
{
po[i] = new Point();
po[i].name = pt[i].name;
po[i].x = pt[i].x - x0;
po[i].y = pt[i].y - y0;
po[i].z = pt[i].z - z0;
}
po[n] = new Point(x0, y0, z0, "ZX");
return po;
}
//重载一些操作符
public static Point operator +(Point m1, Point m2) { return m1.Add(m2); }
public static Point operator -(Point m1, Point m2) { return m1.Sub(m2); }
public static Point operator *(Point m1, double d) { return m1.Mut(d); }
public static Point operator *(double d, Point m1) { return m1.Mut(d); }
public static Point operator /(Point m1, double d) { return m1.Div(d); }
}
public class GPoint
{//Define fields
public string name;
public double h, s;//观测角(弧度表示),边长
public string Name
{ get { return name; } set { name = value; } }
public double H
{ get { return h; } set { h = value; } }
public double S
{ get { return s; } set { s = value; } }
//The constructor
public GPoint(string name = "0", double h = 0, double s = 0)
{
this.name = name;
this.h = h;
this.s = s;
}
}
}
注:现在它已经要依附于角类了:
3. txt->Point[]
/*用sDelim 将str 分割成字符串数组
* @sDelim 可选参数,分隔符
*/
public static string[] Split(string str, string sDelim = null)
{
if(sDelim==null)//默认分割
return str.Split(new string[] { " ", ",", "?", "->", " ","\t" }, StringSplitOptions.RemoveEmptyEntries);
else//根据传入参数分割
return str.Split(new string[] { sDelim }, StringSplitOptions.RemoveEmptyEntries);
}
/*得到一个文本文件的行数
*/
public static int getTextRows(string txt)
{
int n = 0;
StreamReader sR = new StreamReader(txt);
string str = sR.ReadLine();
while (str != null)
{
if (Split(str) != null) n++;
str = sR.ReadLine();
}
sR.Close();
return n;
}
/*读取txt至点数组中
*/
public static Point[] T2Po(string txt)
{
int i = 0, n = getTextRows(txt);
Point[] Pt = new Point[n];
StreamReader sR = new StreamReader(txt);
string str = sR.ReadLine();
while (str != null)
{
string[] sArray = Split(str);
if (sArray != null)
{
Point pt = new Point(sArray);
Pt[i] = pt; i++;
}
str = sR.ReadLine();
}
sR.Close();
return Pt;
}
4. 调用演示
文件数据:
调用代码:
string fo1 = @"你的文件路径";
Point[] po1 = Read.T2Po(fo1);//这里我是把T2Po放到一个Read类里面了。
int n = po1.Length;
for (int i = 0; i < n; i++)
{
po1[i].show();
}
Console.Read();
结果:
#2020/4/25 #
5. 手把手教程
上面就是所有的源码了,有朋友不知道怎么用的,这里补充一下
1.新建一个C# 控制台应用程序,我这里取名叫Hello
2.选中解决方案,然后右键 添加 新建项
选择 类 ,名字改成Point
3.将源码中的代码复制进去
4.新建一个Read 类,将txt->Point[]
中的代码复制进去(或者可以新建个类文件,效果是一样的)注意引用using System.IO;
5.回到main 函数中,将“调用演示”中的代码复制进去,更改文件路径,运行即可
欧了!