领悟旧事

Learned Helplessness
分类新闻>>技术文章>>
学习C#过程中应该注意的若干问题,个个纠结!
来源:http://www.xx0594.com/
时间:2015-6-3
作者:  浏览人数:1187
几天前,接触unity3d,并开始学习C#。unity3d是个全新工具,一切从头开始,摸着石头过河。而对于C#,凭借着C++的基础,弯弯曲曲地前进。因为C#毕竟不同于C++,两者之间的差异,足以让入门者纠结痛苦。
    现在分享解除纠结的方法,以鉴后者。

目录:
1、关于Vector3类型全局变量赋值问题(该方法不对):
2、关于字符串比较问题
3、Vector3数组使用方法。
4、出现“parsing  error”错误的原因及解决方法。
5、关于string截取子串
6、C#关于二维数组
7、防止andorid 程序运行时进入休眠
8、不同场景之间的变量传递
10、NGUI Label赋值问题。
11、新增颜色
12、关于string数组作为public类型的问题

//========================================================
1、关于Vector3类型全局变量赋值问题(该方法不对):
    如果有一个Vector3类型的全局变量vctDir,如果要进行判断赋值,应该借用一个中间变量,不能直接赋值。同时这个中间变

量在定义时要初始化。如下例:

Vector3 dir_go= Vector3.one;//定义一个中间变量。

if(sCmd.Contains("'")) dir_go =new Vector3(1.0f,0.0f,0.0f);//判断赋值给中间变量。
else dir_go =new Vector3(-1.0f,0.0f,0.0f);

mouseCross = dir_go;//再把早间变量赋值给全局变量。


    如果直接赋值的话,会出错。下面的代码得不到正确结果。

if(sCmd.Contains("'")) mouseCross =new Vector3(1.0f,0.0f,0.0f);//判断赋值给中间变量。
else mouseCross =new Vector3(-1.0f,0.0f,0.0f);

    执行后,mouseCross=(0,0,0),而不是想要的结果。
//==================================================================

2、关于字符串比较问题
    比较字符串一般用Contains和IndexOf,但不知道什么原因,用Contains无法正确比较,只能用IndexOf。
如下例:

string sCmd = "F'";

if (sCmd.Contains ("'"))
 mouseCross = Vector3.left; //逆时针旋转。还有一个文档没写但也可以用的left=(-1,0,0)
else
 mouseCross = Vector3.right;//right=(1,0,0)


    结果均为else,也就是无法正确比较。
    而改用IndexOf后,却正确比较。

if (sCmd.IndexOf ("'")>0)
 mouseCross = Vector3.left; //逆时针旋转。还有一个文档没写但也可以用的left=(-1,0,0)
else
 mouseCross = Vector3.right;//right=(1,0,0)


    要注意的是,IndexOf,如果不包含了,则结果为-1.


//==================================================================
3、Vector3数组使用方法。
    代码如下:
Vector3[] cubePos = {new Vector3(1.0f,1.0f,1.0f),new Vector3(-1.0f,1.0f,1.0f),new Vector3(0.0f,1.0f,1.0f),new 

Vector3(1.0f,-1.0f,1.0f),new Vector3(1.0f,-1.0f,0.0f)};

    要注意,组个都要用new来实现。
//==================================================================


4、出现“parsing  error”错误的原因及解决方法。
    出现这个错误,有时候并不是代码出错了。任你代码改就是没办法解决。
    其实原因及处理办法非常简单,只要把中文删除就正常了,包括注释。
    如果一定要用中文注释,请不要用//而要用/*和*/来进行,而且要分行进行注释,如下面代码:

/*
根据旋转面的位置求出旋转的面(哪一个魔方块) 
*/
foreach(GameObject cube in cubes){
  if(cube.transform.position == cubePos[m]){
  cubeObject = cube;
  //break;
 }
}

//==================================================================
5、关于string截取子串
    对string截取子串,有两种情况可以用

情况A:
s ="ABCD";
Console.WriteLine(s[0]); // 输出"A";

情况B:
s ="ABCD";
Console.WriteLine(s.Substring(1)); // 从第2位开始(索引从0开始)截取一直到字符串结束,输出"BCD"
Console.WriteLine(s.Substring(1, 2)); // 从第2位开始截取2位,输出"BC"

    如果只是要截取一个字符,从输出结果看,A和B是一样的。但其实类型是一样,A情况,即用[]下标来取,输出的类型是char

型的,用Substring(1,1)输出的类型是string型的。


//-------------------------------------------------------------------
6、C#关于二维数组

 今天写C#使用2维数组的时候,由于之前写C++的习惯,错写成map[i][j] = num;
 C#的数组访问的正确方式应该是 : map [i,k]=num

 【注意】一个是【i】【k】,另一个是【i,k】

 另外C#的二维数组声明也与C++不同:

  int[,] name = new int[,];
如二维数组:
  string[,] strArray=new string[2,3]{{1,2},{3,4},{5,6}};
访问则要
 strArray[1,6]=4;
//-------------------------------------------------------------------
7、防止andorid 程序运行时进入休眠
    可以入在主摄像机的开始部分。
Screen.sleepTimeout = SleepTimeout.NeverSleep;
//-------------------------------------------------------------------
8、不同场景之间的变量传递
    Unity3d经常存在不同场景,如一个选项场景,按用户选择以后,就要是另一场景实现
用户的选择,此时就涉及一个不同场景之间变量传递的问题。
    首先要在一个场景里存在一些变量,命令如下:

PlayerPrefs.SetInt ("gold", 100);

    之后,再在另一个场景里读取这个变量:
int i=PlayerPrefs.GetInt ("gold",-1);
    如果读取错误,返回-1.

    应用该方面也可以实现不同角本之间的变量传递。
    当然,有用过以后,要及时删除,不然该值会一直存在,影响后续。

PlayerPrefs.DeleteKey ("gold"); 

//-------------------------------------------------------------------
10、NGUI Label赋值问题。
 public UILabel UIlb=null;
    要特别注意,必须将其初始化为null,否则会出错。
(具体使用方法见《NGUI使用初级教程.doc》。
//-------------------------------------------------------------------
11、新增颜色
    Unity3d 的颜色采用RGBA的形式来表示,系统预设的有限几种颜色如Red、Blue等,如果要新增颜色,可以表示如下:
Color myColor = new Color(0.2f,0.2f,0.5f,1.0f);

    这其中,RGBA取值范围在0-1之间。但是,很多颜色的的取值范围都是在1-255之间的整数表示,那么要怎么把1-255的整数转

化为0-1的浮点数呢,请看下面(表示的橙色):Color myColor = new Color(193.0f/255.0f,138.0f/255.0f,0.024f,1.0f
);
    1-255的取值,可以从PS等许多制图软件上得到。

//-------------------------------------------------------------------
12、关于string数组作为public类型的问题
    在C#中,定义string 类型的数组,跟定义其它类型的数组一样,采用
string[] ss= new string[];
    在这里,数组的长度可以不必指明。
    但如果作为public类型的string数组,则必须指明数组长度,否则会出错,所以正确的定法是:
public string[] ss = new string[100];

    问题似乎到此就结束了,我们继续进行以下测试:
public string[] sTotalSteps = new string[200];

string s="DF 12 345 156 012";
   sTotalSteps = s.Split(' ');
   for(int i=0;i<sTotalSteps.Length;i++)
    print(i+":  +"+sTotalSteps[i]+"__");

//结果只输出 5个结果,而并没有输出200个结果。
    
  s="DF 12";
  sTotalSteps = s.Split(' ');
  for(int i=0;i<sTotalSteps.Length;i++)
   print(i+":  +"+sTotalSteps[i]+"__");
//结果只输出 2个结果,而并没有输出5个或200个结果。
    这表明,每次的Split,都会重置数组的长度,而与上次无关。
    还有,更为诡异的是,当我们把
public string[] sTotalSteps = new string[200];
    改为
public string[] sTotalSteps = new string[2];
    后,测试的结果还是一样,也不会出现异常或错误。表明所定义的数组长度没起到应有的作用。

    在这一点上,C#没有C++规范、优雅!
 

关闭窗口
 访问量:508181
任何第三方若要引用、转摘本站信息,均需征得本站书面同意,否则视为侵权。本站信息为个人观点,若因引用本站信息而产生的任何情况,均与本站无关。Email:linmutou@163.com
闽ICP备14017840号-2