Board logo

標題: [分享] visual basic.net 新手教學 [打印本頁]

作者: 呆呆    時間: 2010-5-3 03:52     標題: visual basic.net 新手教學

本帖最後由 呆呆 於 2010-5-9 02:29 編輯

在這裡的前題是,我是用vb2008 Express 版本,有任何操作介面不同的,或找不到對應的,原諒我無法答覆
若您沒有,可到官網下載下載網址


這顯然是最簡單的程式碼,MS 讓WindowsForm程式碼變得簡單,這是讓我們很高興的,他讓我們不用再去煩惱介面的問題,而相對的把時間用在我們要解決的問題上
WindowsForm,有著美麗的外觀,和許許多多的控制項,讓我們可以借由這些已開發好的控制項只經由設定而不用再寫其它的程式碼就可達到相當的功能,當然,在這些控制項的背後
顯然有著無數的程式碼,但那不是我們要關心的了,除非你想要開發專屬於個人的控制項,那你可以覆寫該控制項類別或者是它的父類別或者是祖父類別......等等,但那是另外一回事了
作者: 呆呆    時間: 2010-5-3 05:05

本帖最後由 呆呆 於 2010-5-9 02:31 編輯

當我們鍵入MessageBox. 的時候,會自動出現 show這個方法
而MessageBox所有的成員也只有這個方法,但實際上,show 並不是MessageBox的成員
如果您有仔細看的話,就會看到 , show 這個其實是一個分享函數(有人稱之為靜態函數)
如果我們看到show 的標頭定義,包含了shared這個字
public shared function show(..........) as dialogresult
就可以了解,這個函數其實可以直接透過類別存取,而不用透過實體存取
所以我們不會寫這樣的程式碼    dim x as new messagebox
然後再來 x.show , 這是錯誤的
另外,show這個函數可以傳回 dialogresult 這個數值, 它其實是一個常數,我們會在後面用到它
再者,show其實是一個有20種形態的多載函數,它讓一個函數可以有相同的名稱,卻有著不同的輸入方式
這使得名稱的使用上更具有彈性空間,同樣的動作名稱,卻有者不同的呈現方式,這樣的方式,讓程式碼的
管理更加的方便,以下我們鍵入一個多載的show 方法
  1.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

  2.         If MessageBox.Show("MyFirstProgram", "WindowsForm ", MessageBoxButtons.YesNoCancel, MessageBoxIcon.Information) = Windows.Forms.DialogResult.Yes Then

  3.             MessageBox.Show("成功")
  4.         End If

  5.     End Sub
複製代碼
當然只有我們在按下yes鈕才會動作,而按下yes時就回傳 Windows.Forms.DialogResult.Yes,
WindowsForm就是這麼的簡單
作者: 呆呆    時間: 2010-5-3 22:32

本帖最後由 呆呆 於 2010-5-9 12:56 編輯

寫程式的第一步就是要宣告變數
visual basic 可以讓我們不宣告
但這不是寫程式的良好習慣,變數最好是宣告,讓visual basic 來檢查該變數是否合法
我們可以在程式碼的最上方加入
Option Explicit On ,來強制程式寫作員宣告,
變數最好是有意義的字,就算是中文也沒關係,也就是說,全部都用中文寫,只有關鍵字和保留字是英文也沒關係
因為程式是寫給人看的,所以是愈簡單愈好,除非有著其它因素的的考量,不然最好是寫成一看就知道在寫什麼
利如:
  1. Option Explicit On
  2. Public Class Form1
  3.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

  4.         Dim 時 As Integer
  5.         Dim 分 As Integer
  6.         Dim 秒 As Integer

  7.         時 = Now.Hour
  8.         分 = Now.Minute
  9.         秒 = Now.Second
  10.         MessageBox.Show("現在時刻" & 時 & " 時 " & 分 & " 分 " & 秒 & "秒")
  11.     End Sub
  12. End Class
複製代碼
上面的程式碼中 Dim 時 As Integer 就是宣告,而變數的性質就是整數,整數是一種型別,說型別好像有一點專業,我個人一向不喜歡專業,因為專業好像是要讓人聽不懂
你可以想像成是一種分類,把各種不同的東西加以分類,就是寫程式的基礎,而且也是一種管理
那麼visual basic 有多少種類似於整數的這種分類,以下稍做整理

當然看了以上的宣告就知道我們都可以模仿,利如
dim x as string
就是宣告一個字串
dim x  as single
就是宣告一個單精度的浮點數
所謂的浮點數就是可以帶有小數點以下的數字
或者我們也可以這樣宣告,利用","分開不同資料型態的來宣告
例如: dim x as single, y as double, z as decimal
當然我們也可以一開始就給變數指定值
例如 dim x as single = 3.5,y as string = "Hello World"
另外,我們可以加註解到程式碼中,而編譯時,編譯器就不會去理會這個註解,註解的符號就是 '

利如
dim y as date ' y 是 日期的型態
在 ' 符號後面的文字會被忽略, 讓我們可以用來記錄一些程式碼的目的,或是其它要事
作者: 呆呆    時間: 2010-5-9 00:28

本帖最後由 呆呆 於 2010-5-13 00:16 編輯

我們就來看看幾種資料形態的操作方式

作者: 呆呆    時間: 2010-5-9 01:10

本帖最後由 呆呆 於 2010-5-9 10:31 編輯

也就是我們就自己定了一個時鐘類別,他可以有時,分,秒,而這個類別實際上繼承了object這個所有類別的老祖宗,你不寫也可以
就是這一句    Inherits Object    ' 繼承自 物件
但這是以消費者的觀察而言,他只是想要看到他想要看的的資訊,我要的是幾點幾分
那就生產者而言可就不是這麼回事,時鐘有者很多的零件,時針,分針,各種螺絲
,那麼他可能對於這麼簡單的資料不滿意,因此他想改寫這個類別,但是有時候最令人頭痛的是他沒有
這個類別的原始碼,而只有dll,對他而言,最方便的就是改寫,製造商想做一個報時鈕 , 他所要做的事是這樣,以下是程式碼
  1. Public Class 會報時的時鐘

  2.     Inherits 時鐘

  3.     Public Function 報時() As String

  4.         Return "現在時刻" & Me.時 & "時" & Me.分 & "分" & Me.秒 & "秒"

  5.     End Function
  6. End Class

  7. Public Class Form1

  8.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

  9.         Dim 時鐘 As New 會報時的時鐘

  10.         MessageBox.Show(時鐘.報時)
  11.     End Sub


  12. End Class
複製代碼
這樣,我們很清楚的看到,我們只要繼承原本的時鐘類別,就是得到一個新的報時時鐘,這個時鐘有一個功能,或者稱之為函數,他被包在時鐘之中了
和上面程式碼不同的是,如果我們是從外界看時鐘,那就會寫成不會報時的時鐘樣式,但如果是時鐘可以報時,那就會寫在時鐘類別中而成為會報時的時鐘類別
就是這麼簡單
Function 這個就是函數就意思,而每個Function 之完結會有End Function
表示這個函數到此終結
那麼從外界來看這個程式碼是不是就是成了    Dim 時鐘 As New 會報時的時鐘 ' 我產生的一個會報時的時鐘
MessageBox.Show(時鐘.報時)   '時鐘報時
作者: 呆呆    時間: 2010-5-9 01:34

本帖最後由 呆呆 於 2010-5-13 01:02 編輯

上面還有幾點是要補充的
vb.net 對於函數和程序的方別
函數是可以傳回值的,而程序不能
函數最後的傳回值語法可以是 return 某一個值
或者是 函數定義 = 某一個值
例如 Return "現在時刻" & Me.時 & "時" & Me.分 & "分" & Me.秒 & "秒"
也可以寫成  
報時 = "現在時刻" & Me.時 & "時" & Me.分 & "分" & Me.秒 & "秒"
  1.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

  2.     End Sub
複製代碼
這就是按鈕的程序原型 ,它不會要求傳回值
  1. Public ReadOnly Property 時() As Integer

  2.         Get

  3.             Return Now.Hour

  4.         End Get

  5.     End Property
複製代碼
另外這個稱之為屬性,它讓我們可以存取函數像在存取變收那樣的自然

那windowsform 是類別的話,那他是繼承自 object 嗎
  1. Public Class Form1

  2. End Class
複製代碼
並沒有任何的繼承的樣式,這其實是 MS 為了讓使用者從外觀上看來像是回到了visual basic6的型態
實際上你在方案總管中Form1.desinger.vb中,可以看到
  1. Partial Class Form1
  2.     Inherits System.Windows.Forms.Form
  3. End Class
複製代碼
visual basic 有另外一者使用者自定型態,稱之為結構,其使用方式和class大同小異,就功能上而言,結構無法繼承,這就是結構和類別最大的不同處
不能繼承就代表的是不能覆寫,不能增加屬性,也就是說您沒法在Structure中加入可覆寫的函數或程序,但有趣的一點是,您可以覆寫vb中的一些基本方法,
如tostring,gethashcod,equals,這些是內定的,除此之外,其它的應該都不能覆寫
因此結構只能達到資料的封裝功能,但結構還是有他存在的必要,因為結構是值型別,而不是參照型別,因此
他並不是產生在堆積之上,而類別是參照型別,一些較小的型態利用值型別是比較快的,所以他還是有存在的的必要
以下舉一個值型別的例子:
  1. Public Class Form1

  2.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
  3.         Dim 員工甲 As 員工

  4.         With 員工甲
  5.             .年齡 = 35
  6.             .姓名 = "紀xx"
  7.             .性別 = "不男不女"

  8.             MessageBox.Show(.姓名 & "的年齡是" & .年齡 & ",而性別是" & .性別)
  9.         End With

  10.     End Sub
  11. End Class

  12. Public Structure 員工
  13.    Public 姓名 As String
  14.     Public 年齡 As Integer
  15.     Public 性別 As String
  16. End Structure
複製代碼

作者: 呆呆    時間: 2010-5-9 23:10

本帖最後由 呆呆 於 2010-5-9 23:45 編輯

型別的轉換
我們時常都要型別的轉換
利如,integer轉double或者是轉string
明確的轉換有助於效能的提升,visualbasic 允許程式寫作時不用明確轉換
只要您在程式檔最上頭加上
Option Strict Off
但這並不被建議這樣做,型別的檢查和轉換是有助於防止例外發生的
visual basic 內建了很多型別轉換的函數,如Cint,CDbl,這些函數是在visual basic6就存在的函數名稱
這裡我們介紹一下 Convert 類別內的分享方法
  1. Option Strict On
  2. Option Explicit On
  3. Public Class Form1
  4.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
  5.         MessageBox.Show(Convert.ToString(1 / 7))
  6.         MessageBox.Show((Convert.ToInt32(1 / 7)).ToString)
  7.         MessageBox.Show((Convert.ToSingle(1 / 7)).ToString)
  8.     End Sub
  9. End Class
複製代碼
當然這個類別內還有其它的分享方法,就讓您自己去試驗,但由tostring方法就可以知道,所有的型別幾乎都實作了tostring方法
因此convert.tostring方法似乎都顯得多餘了
,但這些是屬於基本型別的轉換工作,visual basic 在型別上又分為二大類
一個稱之為值型別,另一個稱之為參照型別,像integer,double這種基本型別稱之為值型別
而我們用類別所建立的稱之為參照型別,利如 WindowsForm中的各種控製項都是參照型別
值得一提的是 string 實際上是參照型別,但基於習慣,ms使用一些動作,讓他的寫作語法看起來和值型別一樣
而一般參照型別之間的轉換是用 directcast 函數來轉換,就像以下這樣
  1. Option Strict On
  2. Option Explicit On

  3. Public Class Form1

  4.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

  5.         DirectCast(sender, Button).Text = "轉換成功"
  6.       
  7.     End Sub
  8. End Class
複製代碼

作者: 呆呆    時間: 2010-5-13 01:12

本帖最後由 呆呆 於 2010-5-15 13:19 編輯

可視範圍(scope):
當我們宣告或定義時時常會看到  public ...... ,private..... ,這些被稱之為修飾子
當我們的變數在程序內時不會用 pulic 這程修飾子,我們只會用  dim 來 宣告
該變數並不能被這個程序或者是函數以外程序或函數所存取
當我們的變數或者是函數,程序在類別中或是結構中,或是模組中,只要是前頭被加 private 那就表示
這個變數或程序,函數只能在該類別,結構,模組中存取,而無法由外部存取該變數或程序或方法
反之如果是public,就可被外剖存取,我們就時鐘和form1類別來說,form1是public,所以可以被其它的類別存取
而Sub Button1_Click 是private ,所以只在form1類別內呼叫
Button1_Click程序內的 時鐘變數宣告是用dim(也只能用dim ,因為public ,private 不得用於程序或函數內), 所以只能在程序內使用
而時鐘類別內有三個屬性都是public,但在public 之後又,有readonly表是只能讀,不能存,所以三個屬性都可以被其它類別讀取(不能存)
  1. Public Class Form1
  2.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
  3.         Dim 時鐘 As New 時鐘

  4.         MessageBox.Show("現在時刻" & 時鐘.時 & "時" & 時鐘.分 & "分" & 時鐘.秒 & "秒")

  5.     End Sub

  6. End Class

  7. Public Class 時鐘
  8.     Inherits Object

  9.     Public ReadOnly Property 時() As Integer
  10.         Get
  11.             Return Now.Hour
  12.         End Get
  13.     End Property

  14.     Public ReadOnly Property 分() As Integer
  15.         Get
  16.             Return Now.Minute
  17.         End Get
  18.     End Property

  19.     Public ReadOnly Property 秒() As Integer
  20.         Get
  21.             Return Now.Second
  22.         End Get
  23.     End Property
  24. End Class
複製代碼
生命週期
一個變數在程式中保有他的值的時間就叫做生命週期,一般而言,一個程序或函數執行完時,該函數或程序的所有變數就不存在了,這些變數存在的時間就只有一個函數執行的時間
但如果是全域變數,如利用public 或private 這這修飾子的變數,他們存在的時間就是一整個類別或是應用程式存在的時間,因此當我們要一個變數在一個程序中執行完時還要保留他的值的時候,通常就會使用全域變數
try 看看下面二個程式碼
  1. Public Class Form1

  2.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

  3.         Dim x As Integer
  4.         x = x + 1

  5.         MessageBox.Show(x)

  6.     End Sub

  7.     Private y As Integer
  8.     Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click

  9.         y = y + 1
  10.         MessageBox.Show(y)

  11.     End Sub

  12. End Class
複製代碼
我們很清楚可以看到每按一次button2鈕,y的值就會增加1,但按button1鈕,x值每次的值都是1,這就是因為全域變數不因程序結束就消失,所以y的值每當按一次鈕
結束程序操作時就會加1,但有時候我們不想讓讓別的程序也存取到y,二個程序同時修改到y值造成無法預期的結果如下
  1. Public Class Form1

  2.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

  3.         y = y + 1

  4.         MessageBox.Show(y)

  5.     End Sub

  6.     Private y As Integer

  7.     Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click

  8.         y = y + 1
  9.         MessageBox.Show(y)

  10.     End Sub
  11. End Class
複製代碼
這樣不管我們按 button1 或是 button2 y值都會加1,我只想把y值當成程序內的變數,但又想保留其值,那應該怎麼做
有一程叫靜態變數的東西 其語法如下
Static 靜態變數 as 型態
可以讓你宣告在程序內的變數也可以保留其值以下為範例
  1.    
  2. Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
  3.         Static y As Integer
  4.         y = y + 1
  5.         MessageBox.Show(y)
  6.     End Sub
複製代碼
另外,有一程變數被稱之為常數的變數,這種變數不論你如何改變他都沒用,他是一開始宣就一定要設定起始值,以後均不可變變
否則會有錯誤訊息,該變數宣告方式如下
Const x As Integer = 23
那 x  就是一個常數,而且必需要給起始值23,這個值就一直會是23
作者: 呆呆    時間: 2010-5-15 13:36

本帖最後由 呆呆 於 2010-5-27 23:18 編輯

陣列
當我們要宣告一堆變數而且是同一性質的,我們會他們集合在一起用一個容器給他們然後這個容器有大小,這種容器稱之為陣列
利如 字串甲,乙,丙,丁 不會去這樣宣告
dim 字串甲 as string
dim 字串乙 as string
dim 字串丙 as string
dim 字串丁 as string
我們會宣告一個陣列,其方式如下
dim 字串集合(3) as string
3就是這個字串陣列索引的 上限
而這個字串陣列的索引下很就是0,所以整個字串陣列的字可存取個數為0~3,共有四個
舉個利子
  1. Public Class Form1
  2.     Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
  3.         Dim 一星期(6) As String
  4.         一星期(0) = "星期日"
  5.         一星期(1) = "星期一"
  6.         一星期(2) = "星期二"
  7.         一星期(3) = "星期三"
  8.         一星期(4) = "星期四"
  9.         一星期(5) = "星期五"

  10.         一星期(6) = "星期六"
  11.   MessageBox.Show(一星期(5))
  12.     End Sub
  13. End Class
複製代碼
當然你也可以一開始就給起始值如同一以下範例
陣列內的索引值不用給,直接由後面起始值的數量來決定
  1. Public Class Form1
  2.     Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
  3.         Dim 一星期() As String = {"星期日", "星期一", "星期二", "星期三", "星期四", " 星期五", "星期六"}
  4.         MessageBox.Show(一星期(5))
  5.     End Sub
  6. End Class
複製代碼
您也可以利用迴圈來做一次存取如下
  1. Public Class Form1
  2.     Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

  3.         Dim 一星期() As String = {"星期日", "星期一", "星期二", "星期三", "星期四", " 星期五", "星期六"}

  4.         For Each day As String In 一星期
  5.             MessageBox.Show(day)
  6.         Next
  7.     End Sub
  8. End Class
複製代碼
以上稱為一維陣列,也就是只有一個索引值在陣列中
我們也可以宣告一個二維陣列,那就是   
dim Cell(RowIndex,ColumnIndex) as integer
既然這裡有一堆 Excel 玩家,那用excel儲存格來解式是最快的,一個儲存格的位置在第幾行,第幾列這樣就夠清楚了吧
但excel好像是從第一行開始,而陣列是從第0行開始這是要注意的地方
那三維陣列呢,那就是
dim cell(workSheetIndex,rowindex,columnindex) as integer
也就是去找第幾張工作表中的行列值
那四維的意義呢
dim cell(FileIndex,worksheetindex,rowindex,columndex) as integer
也就是在同一個資料夾內,如果檔名是命成1,2,3的流水號,那就cell(1,2,3,4)的意義就是 第一個檔案中的第二張工作表中的第三列第四行的值
那二維陣列要如何存取
以一下是一個例子
  1. Public Class Form1
  2.     Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

  3.         Dim A(,) As Integer = {{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}, _
  4.                                {11, 12, 13, 14, 15, 16, 17, 18, 19, 20}, _
  5.                                {21, 22, 23, 24, 25, 26, 27, 28, 29, 30}}
  6.         For i As Integer = 0 To A.GetUpperBound(0)
  7.             For j As Integer = 0 To A.GetUpperBound(1)
  8.                 MessageBox.Show(A(i, j))
  9.             Next j
  10.         Next i

  11.     End Sub
  12. End Class
複製代碼
上面程式碼的意思是說,我宣告了一個二維陣列,這個二維陣列是由3個一維陣列所組成
其中每個一維陣列都有10個數
getupperbound(0)回傳a陣列中第一個索引值
getupperbound(1)回傳a陣列中第二個索引值

有時候,我們必需要改變陣列的大小, 因此,我們有一種語法叫 redim 可以變變陣列的大小
以下為範例
  1. Public Class Form1
  2.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
  3.         Dim 可變大小的陣列() As Integer = {1, 2, 3, 4, 5}
  4.         ReDim 可變大小的陣列(10)
  5.         For Each 元素 In 可變大小的陣列
  6.             MessageBox.Show(元素.ToString())
  7.         Next
  8.     End Sub
  9. End Class
複製代碼
我們可以看到,改變後的陣列每個值都是0,但我們有時候想要的是保留原先的值,那要如何做,我們可以加上 Preserve
如下為範例
  1. Public Class Form1

  2.     Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

  3.         Dim 可變大小的陣列() As Integer = {1, 2, 3, 4, 5}

  4.         ReDim Preserve 可變大小的陣列(10)

  5.         For Each 元素 In 可變大小的陣列

  6.             MessageBox.Show(元素.ToString())
  7.         Next
  8.     End Sub
  9. End Class
複製代碼

作者: narita    時間: 2011-9-6 00:40

呆呆 你酷畢了 真是高手 小弟對你的景仰有如滔滔江水綿延不絕又有如黃河氾濫一發不可收拾
正所謂 舉頭望明月 低頭思故鄉 好詩 好詩
作者: Lywspicy    時間: 2020-4-13 09:32

感謝大大,值得納入收藏




歡迎光臨 麻辣家族討論版版 (http://forum.twbts.com/)