執行檔
Shape3D.csabstract class Shape3D
{
//Parameters
protected string name = "";
protected static int amount = 0;
protected double density;
protected int order;
protected Shape3DType.Types shaType;
//Attribute
public string Name
{
get { return name; }
}
public static int Amount
{
get { return amount; }
}
public int Order
{
get { return order; }
set { order = value; }
}
public double Density
{
get { return density; }
set { density = value; }
}
public int ShaType
{
get { return (int)shaType; }
}
//Constructor
public Shape3D(string name, double D)
{
this.name = name;
this.density = D;
amount++;
}
//Method
public double Mass()
{
return Volume() * density;
}
public string displayProperty()
{
string str = Property();
str += string.Format("{0,8:F2}", Volume());
str += '\t';
str += string.Format("{0,8:F2}", Mass());
str += '\t';
return str;
}
//Virtual Method
public abstract double Volume();
public abstract string Property();
}
Shape3DType.csstatic class Shape3DType
{
public enum Types { Unknown = 0, Ball, Cylinder, Square, Pyramid };
}
IRollable.csinterface IRollable
{
double RollingDistances();
}
Ball.csclass Ball : Shape3D, IRollable
{
//--------------Parameters--------------
new private static int amount = 0;
private double radius;
//--------------Attribute--------------
public double Radius
{
get { return radius; }
}
new public static int Amount
{
get { return amount; }
}
//--------------contructor--------------
public Ball(string name, double density, double radius)
: base(name, density)
{
this.radius = radius;
shaType = Shape3DType.Types.Ball;
amount++;
}
~Ball()
{
amount--;
}
//--------------Method--------------
public static Ball Create(string name, double density, double radius)
{
Ball ball = null;
if (density <= 0 || radius <= 0)
return ball;
else
{
ball = new Ball(name, density, radius);
return ball;
}
}
public override double Volume()
{
return Constants.pi * radius * radius * radius * 4.0 / 3.0;
}
public override string Property()
{
string str = "";
str += string.Format("{0,8:F2}", "Ball");
str += '\t';
str += string.Format("{0,8:F2}",radius);
str += '\t';
str += string.Format("{0,8:F2}", "");
str += '\t';
str += string.Format("{0,8:F2}", density);
str += '\t';
return str ;
}
public double RollingDistances()
{
return radius * radius;
}
}
Cylinder.csclass Cylinder:Shape3D,IRollable
{
//--------------Parameters--------------
new private static int amount = 0;
private double radius;
private double height;
//--------------Attribute---------------
public double Radius
{
get { return radius; }
}
public double Height
{
get{return height;}
}
new public static int Amount
{
get { return amount; }
}
//--------------Contructor--------------
public Cylinder(string name, double density,double radius,double height)
: base(name, density)
{
this.radius = radius;
this.height = height;
shaType = Shape3DType.Types.Cylinder;
amount++;
}
~Cylinder()
{
amount--;
}
//--------------Method--------------
public static Cylinder Create(string name, double density, double radius,double height)
{
Cylinder cylinder = null;
if (density <= 0||radius<=0||height<=0)
return cylinder;
else
{
cylinder = new Cylinder(name, density, radius, height);
return cylinder;
}
}
public override double Volume()
{
return radius * radius * Constants.pi* height;
}
public override string Property()
{
string str="";
str += string.Format("{0,8:F2}", "Cylinder");
str += '\t';
str += string.Format("{0,8:F2}", radius);
str += '\t';
str += string.Format("{0,8:F2}", height);
str += '\t';
str += string.Format("{0,8:F2}", density);
str += '\t';
return str;
}
public double RollingDistances()
{
return 5.0 * radius;
}
}
Square.csclass Square:Shape3D
{
//--------------Parameters--------------
new private static int amount = 0;
private double length=0;
//--------------Attribute--------------
public double Length
{
get { return length; }
}
new public static int Amount
{
get { return amount; }
}
//--------------Contructor--------------
public Square(string name, double density, double length):base(name,density)
{
this.length = length;
shaType = Shape3DType.Types.Square;
amount++;
}
~Square()
{
amount--;
}
//--------------Method--------------
public static Square Create(string name, double density, double length)
{
Square square = null;
if (density <= 0 || length <= 0)
return square;
else
{
square = new Square(name, density, length);
return square;
}
}
public override double Volume()
{
return length * length * length;
}
public override string Property()
{
string str = "";
str += string.Format("{0,8:F2}", "Square");
str += '\t';
str += string.Format("{0,8:F2}",length);
str += '\t';
str += string.Format("{0,8:F2}", "");
str += '\t';
str += string.Format("{0,8:F2}", density);
str += '\t';
return str;
}
}
Pyramid.csclass Pyramid:Shape3D
{
//--------------Parameters--------------
new private static int amount = 0;
private double length=0;
private double height=0;
//--------------Attribute--------------
public double Length
{
get { return length; }
}
public double Height
{
get { return height; }
}
new public static int Amount
{
get { return amount; }
}
//--------------Contructor--------------
public Pyramid(string name, double density, double length, double height)
: base(name, density)
{
this.length = length;
this.height = height;
shaType = Shape3DType.Types.Pyramid;
amount++;
}
~Pyramid()
{
amount--;
}
//--------------Method--------------
public static Pyramid Create(string name, double density, double length, double height)
{
Pyramid pyramid = null;
if (density <= 0 || length <= 0 || height <= 0)
return pyramid;
else
{
pyramid = new Pyramid(name, density, length, height);
return pyramid;
}
}
public override double Volume()
{
return 1.0/3.0 * length * length * height;
}
public override string Property()
{
string str = "";
str += string.Format("{0,8:F2}", "Pyramid");
str += '\t';
str += string.Format("{0,8:F2}", length);
str += '\t';
str += string.Format("{0,8:F2}", height);
str += '\t';
str += string.Format("{0,8:F2}", density);
str += '\t';
return str;
}
}
Form.cs
public partial class Form1 : Form
{
List arrShape = new List();
string str = "";
public Form1()
{
InitializeComponent();
lbl_label1.Visible = false;
lbl_label2.Visible = false;
txt_Height.Visible = false;
txt_Length.Visible = false;
txt_Radius.Visible = false;
}
private void cbox_ShapeSelect_SelectedIndexChanged(object sender, EventArgs e)
{
switch (cbox_ShapeSelect.SelectedIndex)
{
case 0:
lbl_label1.Text = "半徑";
lbl_label1.Visible = true;
lbl_label2.Visible = false;
txt_Radius.Visible = true;
txt_Height.Visible = false;
break;
case 1:
lbl_label1.Text = "半徑";
lbl_label2.Text = "高度";
lbl_label1.Visible = true;
lbl_label2.Visible = true;
txt_Radius.Visible = true;
txt_Height.Visible = true;
txt_Length.Visible = false;
break;
case 2:
lbl_label1.Text = "邊長";
lbl_label1.Visible = true;
lbl_label2.Visible = false;
txt_Length.Visible = true;
txt_Radius.Visible = false;
txt_Height.Visible = false;
break;
case 3:
lbl_label1.Text = "邊長";
lbl_label2.Text = "高度";
lbl_label1.Visible = true;
lbl_label2.Visible = true;
txt_Length.Visible = true;
txt_Height.Visible = true;
txt_Radius.Visible = false;
break;
default:
break;
}
}
private void btn_Add_Click(object sender, EventArgs e)
{
if (cbox_MatelSelect.SelectedIndex==-1)
{
MessageBox.Show("請選擇材質");
return;
}
//int amount=Shape3D.Amount;
switch (cbox_ShapeSelect.SelectedIndex)
{
case 0:
if (txt_Radius.Text == "")
{
MessageBox.Show("請輸入參數");
return;
}
Ball ball = Ball.Create(cbox_ShapeSelect.Text, DensityofMatel.ChooseDensity(cbox_MatelSelect.SelectedIndex), double.Parse(txt_Radius.Text));
if (ball == null)
{
MessageBox.Show("參數輸入錯誤");
return;
}
ball.Order = arrShape.Count;
arrShape.Add(ball);
break;
case 1:
if (txt_Radius.Text == "" || txt_Height.Text == "")
{
MessageBox.Show("請輸入參數");
return;
}
Cylinder cylinder = Cylinder.Create(cbox_ShapeSelect.Text, DensityofMatel.ChooseDensity(cbox_MatelSelect.SelectedIndex), double.Parse(txt_Radius.Text), double.Parse(txt_Height.Text));
if (cylinder == null)
{
MessageBox.Show("參數輸入錯誤");
return;
}
cylinder.Order = arrShape.Count;
arrShape.Add(cylinder);
break;
case 2:
if (txt_Length.Text == "")
{
MessageBox.Show("請輸入參數");
return;
}
Square square = Square.Create(cbox_ShapeSelect.Text, DensityofMatel.ChooseDensity(cbox_MatelSelect.SelectedIndex), double.Parse(txt_Length.Text));
if (square == null)
{
MessageBox.Show("參數輸入錯誤");
return;
}
square.Order = arrShape.Count;
arrShape.Add(square);
break;
case 3:
if (txt_Length.Text == "" || txt_Height.Text == "")
{
MessageBox.Show("請輸入參數");
return;
}
Pyramid pyramid = Pyramid.Create(cbox_ShapeSelect.Text, DensityofMatel.ChooseDensity(cbox_MatelSelect.SelectedIndex), double.Parse(txt_Length.Text), double.Parse(txt_Height.Text));
if (pyramid == null)
{
MessageBox.Show("參數輸入錯誤");
return;
}
pyramid.Order = arrShape.Count;
arrShape.Add(pyramid);
break;
default:
MessageBox.Show("請選擇形狀");
return;
}
str += arrShape[arrShape.Count - 1].Property() + Environment.NewLine;
txt_list.Text = str + ShowProperty();
ShowAmount();
}
private void btn_cancel_Click(object sender, EventArgs e)
{
if (txt_cancel.Text == "")
{
MessageBox.Show("請輸入編號");
return;
}
int order = int.Parse(txt_cancel.Text);
if (arrShape.Count <= order)
{
MessageBox.Show("無此編號,請重新輸入");
return;
}
arrShape[order] = null;
GC.Collect();
GC.WaitForPendingFinalizers();
arrShape.RemoveAt(order);
RestSerialNumber();
ShowAmount();
txt_list.Text = Showlist();
}
private void btn_Caculus_Click(object sender, EventArgs e)
{
for (int i = 0; i < arrShape.Count; i++)
{
string str = (arrShape[i].displayProperty() + Environment.NewLine);
txt_ShowCaculusRsults.AppendText(str);
}
txt_ShowCaculusRsults.AppendText(ShowProperty() + string.Format("{0,8}", "體積") + "\t" + string.Format("{0,8}", "重量") + Environment.NewLine);
}
private void btn_CaculusRoll_Click(object sender, EventArgs e)
{
foreach (var shape in arrShape)
{
IRollable roll = shape as IRollable;
if (roll != null)
{
txt_DisplayRolling.AppendText(shape.Property() + string.Format("{0,8}", roll.RollingDistances()) + Environment.NewLine);
}
}
txt_DisplayRolling.AppendText(ShowProperty() + string.Format("{0,8}", "滾動的距離") + Environment.NewLine);
}
private void cbox_Sort_SelectedIndexChanged(object sender, EventArgs e)
{
Sort();
txt_list.Text = Showlist();
}
private string Showlist()
{
string str="";
for (int i = 0; i < arrShape.Count; i++)//重新顯示物件
{
str += arrShape[i].Property() + Environment.NewLine;
}
str+=ShowProperty();
return str;
}
private void Sort()//排序
{
switch (cbox_Sort.SelectedIndex)
{
case 0:
arrShape.Sort(CompareByOrder);
break;
case 1:
arrShape.Sort(CompareByType);
break;
case 2:
arrShape.Sort(CompareByDensity);
break;
case 3:
arrShape.Sort(CompareByVolume);
break;
case 4:
arrShape.Sort(CompareByMass);
break;
default:
break;
}
RestSerialNumber();
}
private int CompareByOrder(Shape3D a, Shape3D b)//按照加入順序
{
if (a.Order > b.Order)
return 1;
return -1;
}
private int CompareByType(Shape3D a, Shape3D b)//按照形狀
{
if (a.ShaType > b.ShaType)
return 1;
return -1;
}
private int CompareByDensity(Shape3D a, Shape3D b)//按照材質
{
if (a.Density > b.Density)
return 1;
return -1;
}
private int CompareByVolume(Shape3D a, Shape3D b)//按照體積
{
if (a.Volume() > b.Volume())
return 1;
return -1;
}
private int CompareByMass(Shape3D a, Shape3D b)//按照重量
{
if (a.Mass() > b.Mass())
return 1;
return -1;
}
private void RestSerialNumber()//重新編號
{
for (int i = 0; i < arrShape.Count; i++)
{
arrShape[i].Order = i;
}
}
private string ShowProperty()
{
string str = "";
str += Environment.NewLine;
str += string.Format("{0,8}", "編號");
str += string.Format("{0,8}", "型別");
str += string.Format("{0,8}", "邊長(半徑)");
str += string.Format("{0,4}", "高");
str += '\t';
str += string.Format("{0,5}", "密度");
str += '\t';
return str;
}
private void ShowAmount()//顯示數量
{
txt_BallAmount.Text = Ball.Amount.ToString();
txt_CylinderAmount.Text = Cylinder.Amount.ToString();
txt_SquareAmount.Text = Square.Amount.ToString();
txt_PyramidAmount.Text = Pyramid.Amount.ToString();
txt_Amonut.Text = arrShape.Count.ToString();
}
}
第四組
回覆刪除連用2個鋁球 按創造順序排 在按計算就掛了 跟我一樣= =
把a.ShaType > b.ShaType的>變>=說不定就可以了
刪除我們測試的結果並沒有你說的問題......
刪除@施文浩:
刪除你是在XP的作業系統執行程式嗎? 我們這組測試過,XP會有這種問題,Win7沒有. C#是用2010的.
初步研究後,可能是List.Sort()內部使用的排序方法不同造成的影響.
不過只要加入判斷"相同數值"的情況,程式就可以過.
所以寫比較器最好還是把>,=,<三種情況都考慮進去.
我覺得這份已經算是蠻完整的程式,而且也沒有太大的問題,但我認為有些地方可以再加強,因此用條列的方式說明如下:
回覆刪除———————————————————————————
1.
根據規則:
2.2 Name Usage & Syntax
Field: Avoid using non-private Fields!
問題點:
Shape3D 第4~8行
建議:
protected 修改成 private,並在屬性設定權限。
———————————————————————————
2.
根據規則:
1.4.1 Naming Conventions
Field
Protected: P
Private: _c
問題點:
Shape3D 第4~8行
Ball 第4~5行
Cylinder 第4~6行
Square 第4~5行
Pyramid 第4~6行
建議:
若使用protected,則欄位使用帕斯卡命名法;若修改成private,則建議加底線於字首前 (_)。
———————————————————————————
3.
根據規則:
3.1 Formatting
Rule 8.
Group internal class implementation by type in the following order:
a. Member variables.
b. Constructors & Finalizers.
c. Nested Enums, Structs, and Classes.
d. Properties
e. Methods
問題點:
Shape3D 第9~38行
Ball 第6~26行
Cylinder 第7~32行
Square 第6~25行
Pyramid 第7~32行
建議:
建議將Constructor寫在Properties前面,以符合規定。
———————————————————————————
4.
根據規則:
2.2 Name Usage & Syntax
Method
Try to use a Verb or Verb-Object pair.
問題點:
Shape3D 第40行
Shape3D 第54行
Shape3D 第56行
IRollable 第3行
建議:
方法命名時建議加入動詞。
———————————————————————————
5.
根據規則:
1.4.1 Naming Conventions
Method
Public: P
問題點:
Shape3D 第44行
建議:
displayProperty 修改成 DisplayProperty。
———————————————————————————
6.
根據規則:
Logic error.
問題點:
創建4個物件,然後移除2次編號0的物件,再創建1個物件,接著依照創建順序排序,其排序結果有誤。
建議:
修改ball.Order = arrShape.Count;
cylinder.Order = arrShape.Count;
square.Order = arrShape.Count;
pyramid.Order = arrShape.Count;
———————————————————————————
7.
根據規則:
3.1 Formatting
Rule 4.
Always use curly braces ({ and }) in conditional statements.
問題點:
Form1 第141行
Form1 第207行
Form1 第213行
Form1 第219行
Form1 第225行
建議:
即使只有一行,仍然建議使用大括號。
———————————————————————————
8.
根據規則:
4.2 Variables & Types
Rule 7.
Try to initialize variables where you declare them.
問題點:
Shape3D 第6~7行
Ball 第5行
Cylinder 第5~6行
建議:
建議在宣告時加入初始值。