第7章 C#中的文件,數組和異常


 第7章 C#中的文件,數組和異常

C#處理數組和文件相當容易,並引入異常來簡化錯誤處理。


7.1 數組

const int MAX=10;
float[] xy=new float[MAX];
for (int i=0;i<MAX;i++){
 xy[i]=i;
}
應當習慣數組的循環是從零到數組邊界值減1,正如我們在前面的代碼中所做的那樣。
所有的數組變量都有一個長度屬性,可以根據它查出數組的大小。
float[] z=new float[20];
for (int j=0;j<=z.length;j++){
 z[j]=j;
}
C#中的數組是動態的,可以在任何時候重新分配空間。
在類內部創建一個數組的引用,然后分配空間,可這樣寫:
float[] z;  //declare here
z=new float[20]; //create later


7.2 集合對象

7.2.1 ArrayList

ArrayList(數組表)對象本質上是一個可變長的數組,可以根據需要添加元素
使用ArrayList的方法可以向數組中添加元素,或取出,修改某個元素.
float[] z={1.0f,2.9f,5.6f};
ArrayList arl=new ArrayList();
for (int j=0;j<z.length;j++){
 arl.Add(z[j]);
}
ArrayList有一個Count屬性,可用於確定它所包含的元素數目.
for (j=0;j<arl.count;j++){
 Console.WriteLine(arl[j]);
}
foreach(float a in arl){
 Console.WriteLine(a);
}

ArrayList的方法列表:
Clear
刪除ArrayList的內容

Contains(object)
如果ArrayList包含該對象,則返回true

CopyTo(array)
將ArrayList全部內容拷貝到一個一維數組中

IndexOf(object)
返回該對象的第一個索引值

Insert(index,object)
將元素插入到指定的位置

Remove(object)
從表中刪除該元素

RemoveAt(index)
刪除指定對象的元素

Sort
對ArrayList排序


從ArrayList中取出的每個對象都是object類型,這就意味着,在使用前通常需要將其轉換成合適的類型.
float x=(float)arl[j];


7.2.2 Hashtable 哈希表

Hashtable是一個可變長數組,表中的每個項目都通過關鍵字值來訪問.
關鍵字一般是某個字符串,也可以是其他類型的對象.
使用Hashtable可以快速訪問一個大而無序的記錄表
還可以將關鍵字和項目值顛倒過來,創建一個每條項目都是唯一的表.

Hashtable hash=new Hashtable();
float freddy=12.3f;
hash.Add("fred",freddy); //add to table
//get this one back out
float temp=(float)hash["fred"];

注意,同ArrayList一樣.從Hashtable中得到的數據也必須轉換成合適的類型
Hashtable也有一個Count屬性,可用來獲取關鍵字的列表或項目的列表.


7.2.3 SortedList

SortedList(排序表)類保存了兩個內部數組,可以通過基於零的下標或字母關鍵字來獲取元素.
float sammy=44.55f;
SortedList slist=new SortedLIst();
slist.Add("fred",freddy);
slist.Add("sam",sammy);

//get by index
float newFred=(float)slist.GetByIndex(0);

//get by key
float newSam=(float)slist["sam"];

在System.Collections名字空間還可以看到Stack(堆棧)對象和Queue(隊列)對象,
他們的特性和讀者期望一樣,可以在系統幫助文檔中找到他們的方法.


7.3 異常

C#用異常完成錯誤處理,而不是采用其他難以使用的錯誤檢測方法。
異常處理就是把引起錯誤的語句包含在try塊中,然后用catch語句捕獲錯誤.
try{
 //Statements
}
catch(Exception e){
 //do these if an error occurs
finally{
 //do these anyway
}
一般使用這種方法檢查文件處理語句的錯誤,
也可以用語捕獲數組下標越界和許多其他錯誤情形。
執行try塊中的語句若無錯誤,則轉到finally語句;
若有錯誤,則轉到catch語句,然后轉到finally語句.
try{
 //note-one too many
 for(int i=0;i<=arl.count(arl[i]);
}
catch(Exception e){
 Console.WriteLine(e.Message);
}
這段程序輸出了錯誤信息和程序中的調用位置,然后繼續運行.
相反,若不捕獲異常,運行時會給出一條錯誤信息.
程序將退出運行不再繼續下去並給出出錯界面.

C#中的常用異常類

AccessException
訪問類的方法或數據時出錯

ArgumentException
傳給方法的參數是無效的

ArgumentNullException
參數是空的

ArithmeticException
上溢或下溢

DivideByZereException
被0除

IndexOutOfRangeException
文件沒找到

EndOfStreamException
訪問超出了輸入數據流(如文件)的末端

DirectoryNotFoundException
目錄沒找到

NullReferenceException
對象變量沒有初始化成一個實際的值


7.4 多個異常

也可以在一系列catch塊中捕獲多個異常並分別進行處理:
try{
 for(int i=0;i<=arl.count;i++){
  int k=(int)(float)arl[i];
  Console.Write(i+""+k/i);
 }
}
catch(DivideByZereException e){
 printZero(e);
}
catch(IndexOutofRangeException e){
 printOErr(e);
}
catch(Exception e){
 printErr(e);
}
這樣做可以讓程序以不同方式從各種錯誤中恢復過來.


7.5 拋出異常

try{
 //statements
}
catch(Exception e){
 throw(e); //pass on to calling program
}

7.6 文件處理

C#中的文件處理對象提供了一些相當靈活的處理文件的方法.

7.6.1 File對象

File(文件)對象代表一個文件,並為檢測文件是否存在,文件更名和文件刪除提供了一些有用的方法。
所有這些方法都是靜態的,也就是說,
不能使用new運算符創建file的實例,但可以直接使用File的方法.

if(File.Exists("Foo.txt"))
 File.Delete("foo.txt");

用File對象獲得用於讀寫文件數據的文件流(FileStream)

//open text file for reading
StreamReader ts=File.OpenText("foo1.txt");

//open any type of file for reading
FileStream fs=File.OpenRead("foo2.any");

一些比較有用的File方法:

File.FileExists(filename)
若文件存在,則為true

File.Delete(filename)
刪除該文件

File.AppendText(String)
添加文本

File.Copy(fromFile,toFile)
拷貝一個文件

File.Move(fromFile,toFile)
移動文件,刪除舊文件

File.GetExtension(filename)
返回文件的擴展名

File.HasExtension(filename)
若文件有擴展名,則為true


7.6.2 讀文本文件

StreamReader ts=File.OpenText("foo1.txt");
string s=ts.ReadLine();

7.6.3 寫文本文件

//open for writing
StreamWriter sw=File.CreateText("foo3.txt");
sw.WriteLine("Hello file");

7.6.3 寫文本文件

//append to text file
StreamWriter asw=new StreamWriter("foo1.txt",true);
//true為用於追加的布爾參數

7.7 文件處理中的異常

try{
 //open text file for reading
 StreamReader ts=File.OpenText("foo1.txt");
 string s=ts.ReadLine();
}
catch(Exception e){
 Console.WriteLine(e.Message);
}

7.8 檢測文件末尾

private StreamReader rf;
private bool eof;
public String readLine(){
 String s=rf.ReadLine();
 if(s==null)
  eof=true;
 return s;
}
public bool fEof(){ //文件讀入類中創建一個文件結束函數
 return eof;
}

另外一種保證讀數據不會超過文件末尾的方法:
Peek方法返回文件中下一個字符的Ascii碼,如果沒有字符則返回-1.
public String read_Line(){
 String s="";
 if(rf.Peek()>0){
  s=rf.ReadLine();
 }
 else{
  eof = true;
 }
 return s;
}

7.9 csFile類

將文件方法包裝在一個帶有易用方法的簡單類中會更方便,於是我們編寫了csFile類
這里把文件名fileName和路徑包含在構造函數里,也可以用重載的OpenForRead和OpenForWrite語句把它傳遞進來.
public class csFile{
 private string fileName;
 StreamReader ts;
 StreamWriter ws;
 private bool opened,writeOpened;
 public csFile(){
  init();
 }
 private void init(){
  opened=false;
  writeOpened=false;
 }
 public csFile(string file_name){
  fileName=file_name;
  init();
 }
 //打開用於讀數據的文件
 public bool OpenForRead(string file_name){
  fileName=file_name;
  try{
   ts=new StreamReader(fileName);
   opened=true;
  }
  catch(FileNotFoundException e){
   return false;
  }
  return true;
 } 
 //接下來,可以用readLine方法從文本文件讀數據
 public string readLine(){
  return ts.ReadLine();
 }
 //打開一個用於寫數據的文件,並向其中寫入若干文本:
 public void writeLine(string s){
  ws.WriteLine(s);
 }
 public bool OpenForWrite(string file_name){
  try{
   ws=new StreamWriter(file_name);
   fileName=file_name;
   writeOpened=true;
   return true;
  }
  catch(FileNotFoundException e){
   return false;
  }
 }
}
在任何需要讀寫文件時,都會使用這個簡化的文件方法包裝類.


注意!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系我们删除。



 
粤ICP备14056181号  © 2014-2020 ITdaan.com