官术网_书友最值得收藏!

2.3 數據類型

在MCGSE中,數據類型非常簡單,只有三種,即開關型、數值型和符號型,這與C、Visual Basic、C#等高級語言的數據類型大不相同,進行了簡化。開關型變量相當于大家熟知的整型變量,數值型變量相當于單精度浮點型變量,字符型變量相當于字符串變量。

(1)開關型變量 開關型變量是指0或非0的整數,把整數分成了兩部分,像3、-5等都屬于非0值。開關型變量相當于C語言中的整型變量,由4個字節構成,4個字節共計32個位(4字節×8位/字節),分為正、負兩部分,正數有231個,范圍是0~(231-1),負數有231個,范圍是-231~-1,整個數值范圍是-231~(231-1)。MCGSE組態軟件經常輸出控制某個開關量,例如電磁閥、繼電器、光電開關等,如果某個開關型變量與繼電器相關聯,當這個變量的值為非0(1、2、-3、1000等)時,系統會輸出高電平給繼電器,繼電器獲得高電平電壓后便可打開,相當于給繼電器通電;相反,如果變量的值為0,則繼電器獲得低電平,繼電器關閉,相當于斷電。因此,非0就表示開,0表示關。開關型變量如果僅用于開關量,那它的功能僅用了一小部分,實際上開關型變量主要用于整數,如,!I2Ascii、!I2Bin、!I2Hex、!I2Oct等函數中的字母“I”表示“Integer”,即整數的意思,這些函數的輸入參數為開關型變量,但是從功能上看,是將整數轉化為ASCII碼、將整數轉化為二進制、將整數轉化為十六進制、將整數轉化為八進制。因此,仍然是將開關型變量當作整數使用了。可參考二維碼視頻講解。

(2)數值型變量 帶小數點或不帶小數點的數值,如:12.45,100。屬于單精度浮點型,占4個字節(32位)內存空間,其數值范圍為-3.4×10-38~3.4×1038,只能提供七位有效數字。

(3)字符型變量 最多512個字符組成的字符串,采用英文雙引號包含。如:“合抱之木,生于毫末;九層之臺,起于累土;千里之行,始于足下。”“NO pains! NO gains!”等,使用字符串變量需要注意的是必須采用“英文雙引號”,中文雙引號雖然也是引號,但是在計算機語言中被當成字符處理,就像“ABC、中華人民共和國”等字符一樣,不是關鍵字。因此,使用字符型變量時一定要十分小心!

2.3.1 開關型

開關型即整型,由4個字節構成,如圖2-4所示,采用補碼方式存儲,從右向左數,第一位為0位,第二位為1位,第三位為2位,……,最后一位為31位。最高位31位表示正、負號,“1”表示負號,“0”表示正號。

正數的補碼是其本身,如+1、+4096,分別用正數的二進制數表示,例如,6378是正數,對應的二進制位最高位是0,轉換為二進制編碼為:

圖2-4 開關型數據(整數)編碼示意圖

(0000 0000 0000 0000 0001 1000 1110 1010)→+6378

負數的補碼為負數絕對值對應二進制取反再加1,例如,-4096的絕對值為4096,對應的二進制編碼為:

(0000 0000 0000 0000 0001 0000 0000 0000)→+4096

(1111 1111 1111 1111 1110 1111 1111 1111)→+4096取反

(1111 1111 1111 1111 1111 0000 0000 0000)→+4096取反+1

MCGSE對開關型數據采用字符串進行轉化,如下面函數!Hex2I(s)所示。

函 數 名:!Hex2I(s)。

函數意義:把16進制字符串轉換為數值。

返 回 值:開關型。

參數:s, 字符型。

實例:!Hex2I("11") =17。

“!”表示一個函數的開始,這是MCGSE系統對函數的約定,實際上,MCGSE采用的是一種類Basic的語言,對底層函數進行了封裝,減弱了原始語言的靈活性,增加了用戶使用的方便性。“Hex”是英文“hexadecimal”的前三個字母,意思是“十六進制”,“2”的英文發音與“to”相同,意思是轉換,“I”是英文“Integer”(整數)的首字母,所以上述函數的意思是將一個字符串形式的16進制數轉化為一個整數(開關型)。如果十六進制超范圍會怎樣呢?MCGSE系統會自動截斷,比如:

!Hex2I("FF11223344")=287454020=!Hex2I("11223344"),前面的“FF”被截去了,所以并不會出現溢出錯誤,說明MCGSE對數據范圍進行了預處理。“287454020”就是對應十六進制數“11223344”的十進制數。

如果輸入的是非十六進制字符串,會當作“0”處理,例如:

!Hex2I("MNOPQ")=0。

在函數書寫過程中,注意三點:第一,前面的“!”不能省略;第二,函數后面的括號必須是英文括號“()”,這有別于中文括號“()”,一個窄,一個寬;第三,括號內十六進制要用英文雙引號引起來,也不能用中文雙引號。下述幾個例子是錯誤的:

Hex2I("FE32")   (Χ);沒有“!”, 前面應該加“!”。

!Hex2I("FE32")          (Χ);括號為中文括號, 應該為英文括號。

!Hex2I(“FE32”)          (Χ);雙引號為中文雙引號, 應該為英文雙引號。

2.3.2 數值型

在C/C++語言中,實型分為單精度浮點型和雙精度浮點型兩種。在MCGSE中,數值型指的是單精度浮點型,數據采用單精度浮點型(float)存儲時,占用32個比特(bit)位,即4個字節寬度。單精度浮點型數據在存儲方式上遵循電氣電子工程師協會(Institute of Electrical and Electronics,IEEE)頒布的754標準,其存儲格式如圖2-5所示,圖中的“*”表示可正可負,在存儲中可分為以下三個部分:

圖2-5 單精度實型存儲格式

(1)符號位(sign) 符號位是存儲空間中最左邊的1個位,即第31個位,用0代表正,1代表負,為了便于記憶,可以認為“1”是負號“-”豎起來的一種形式,這樣就不會將正、負混淆。

(2)指數部分(exponent) 用科學記數法表示實數時,其形式為a×10n,其中1≤|a|<10。n是整數,表示指數。指數部分表示冪n的位區間,占用存儲空間中的第23~30位,共計8個位。

(3)尾數部分(mantissa) 尾數部分表示科學記數法中尾數a的位區間,占用存儲空間中的第0~22位,共計23個位。此外,浮點數有兩個例外,數0.0存儲為全零;無限大數的符號位指示正無窮或者負無窮,指數部分存儲為全1,尾數部分全零。可參考二維碼視頻講解。

顯然,用科學記數法表示實數時,采用的是十進制,例如,8.125用科學記數法表示為8.125×100,-42.5用科學記數法表示為-4.25×101。但是,計算機以二進制形式存儲數據,只能出現0或1。因此,要將待存儲的數用二進制的科學記數法表示,其形式為±1.xxx…×2n,其中n表示8個位的二進制指數,xxx…為23個位的二進制尾數。由于尾數中沒有包括小數點前面的“1”,實際上尾數表示的值為1.xxx…,這樣,23個位就能夠表示24個位的數值,2(23+1)=16777216,由于107 < 16777216 < 108,因此,單精度浮點數的有效位數是7位。

IEEE754規定,浮點型數據對應的機器數表示形式為±1.xxx…×2n,其尾數部分采用了規范化格式1.xxx…,而不是0.xxx…,這樣導致整個浮點型數據由±0.xxx…×變為1.xxx…×2n,指數部分由n+1減為n,變為機器數時,指數部分的n和尾數部分小數點以后的部分參與編碼,此時,尾數小數點前的1不參加編碼,但實際上表示的含義已經包括進去了,相當于尾數部分首位1會隱藏掉,例如,指數部分為3(0000 0011)時,相當于128(1000 0000)加上3,結果為131(10000 0011),由于尾數部分進行了左移,指數部分可以減少1,把尾數的首位數字1隱去,所以131實際上是130,相當于128+2=127+3,為便于記憶直接稱為127移碼。對于8個位的二進制指數部分,其表示范圍為0~(28-1),即0~255,如圖2-6所示,把這個8位二進制數看成無符號數,再減去127,此時表示的范圍應該為-127~128,即-(27-1)~27

圖2-6 指數部分原數據移位存儲過程示意圖

根據單精度存儲格式可知,指數部分最大值為255,表示無窮大,除此之外,比255小的最大數為254,這個數值為移位存儲的數據,原數據為254-127=127,所以單精度浮點數可以表示的范圍為±3.4028235×1038(±1.1111…1×2127),由于采用的是二進制,此處的1.1111…1實際上是1+1/2+1/4+1/8+1/16+…+1/(2×23),這是個等比數列,其累加和應該為1×(1-1/224)/(1-1/2)=2×(1-1/224)= 1.99999988079071044921875,而2127為1.7014118346046923173168730371588×1038。因此,±1.1111…1×2127所能表示的范圍為是±3.4028235×1038。對于接近于0的最小值,由于指數部分全為零表示0.0,比0大的最小數為1,這個數值也是移位存儲的數據,原數據應為1-127=-126,因此,單精度浮點型數據可以表示的最小數為±1.17549×10-38(±1.00…0×2-126)。圖2-7給出了采用單精度浮點型數據存儲時所能表示的數值范圍,從圖中可以看出,其范圍并不是連續的,其中0.0、正無窮和負無窮為孤立點,正數區間和負數區間為“連續區”,實際上用數字表示實數是一種將連續量表示為離散量的過程。因此,這里的“連續區”是“連貫”的離散區,細小到兩個相連的小數時仍然具有間隔。可參考二維碼視頻講解。

圖2-7 單精度浮點型數據存儲范圍示意圖

為了清楚地說明單精度浮點型數據在計算機中的存儲格式,下面分別以+8.125和-42.25兩數為例,詳細介紹其轉化為二進制數據的過程,如圖2-8所示,該過程分為五個步驟:

圖2-8 單精度浮點型數據轉換為計算機二進制數的過程示意圖

第一步,將待存儲的數字用帶有符號的形式表示出來,如8.125為+8.125。

第二步,以小數點為間隔,將數字分為前后兩部分,前半部分為整數,后半部分為小數。整數按“除2取余,自下而上”法轉化為二進制,如8.125中前半部分為8,8除以2,余數為0,商為4;4除以2余數為0,商為2;2除以2余數為0,商為1;1除以2余數為1,商為0,整理余數部分,8轉化為二進制數1000。小數按“乘2取整,自上而下”法轉化為二進制,如8.125中后半部分為0.125,0.125乘以2,整數部分為0,小數部分為0.25;0.25乘以2,整數部分為0,小數部分為0.5;0.5乘以2,整數部分為1,小數部分為0,整理整數部分,0.125轉化為二進制數0.001。

第三步,將數字二進制小數點前半部分加上后半部分,獲得完整的二進制表示形式,8.125即可表示為1000.001,這一步需要注意的是:取余和取整時應按圖2-8中箭頭所示方向安排順序,不能顛倒。然后將二進制數字用二進制科學記數法來表示,其結果為1.000001×23

第四步,按單精度存儲格式對上述二進制數字進行變換,“+”表示正號,說明第31位為0;指數為3,用3加上127得130,將130轉化為二進制數1000 0010;尾數部分為去掉小數點前的1以后剩下的部分,如果不足23位,其余位用0補充,如果超過23位,則去掉23位以后的數字。按照“符號位+指數位+尾數位”格式寫出二進制編碼“0+1000 0010+0000 0100 0000 0000 0000 000”。

第五步,將符號位、指數部分和尾數部分的二進制數合在一起,共計32個位,每8個位構成一個字節,即“01000001 00000010 00000000 00000000”,每個字節前4位和后4位分別用十六進制數表示,即“41 02 00 00”,這個數就是8.125在計算機中的存儲形式。

同理,按上述方法,也可將-42.25轉化為“C2 29 00 00”。可參考二維碼視頻講解。

2.3.3 字符型

MCGSE中的字符型數據實際上是字符串,即是采用英文雙引號包括起來的各種可顯示符號,如數字、大小寫英文字母、標點符號、漢字等。操作字符型的函數可以分為兩大類,一類是字符串操作函數,如圖2-9所示;另一類為字符型數據與開關型和數值型數據相互轉換函數,如圖2-10所示。

圖2-9 MCGSE中字符型數據操作函數統計圖

圖2-10 MCGSE中字符型數據與開關型和數值型數據相互轉換函數對比圖

字符串操作函數包括字符串比較函數、字符串長度計算函數、字符串截取函數、字符串統一大小寫函數和字符串去空格函數,在這些函數中,字符串長度計算函數較特殊,這個函數的功能是獲得字符串的長度,對于ASCII碼而言,其長度相當于對應字母、數字或符號的個數,但是,對于漢字,其長度相當于2倍的漢字個數。例如,“中國”這個字符串,如果用!Len("中國")計算字符串長度,值為4。計算機內部存儲漢字時采用的是GBK碼,一個漢字用兩個字節來表示,“中”的GBK碼為“D6 D0”,“國”的GBK碼為“B9 FA”。所以“中國”字符串的長度為4,即4個字節長度。有趣的是,在字符串截取函數中,指示要截取幾個的數字又表示完整的漢字,例如,!Left("中國China",4)的結果為"中國Ch",在這個函數中,4又表示4個完整的字符數,即"中國Ch"這4個字符,而不是字節數。因此,需要大家細心甄別,掌握MCGSE函數的使用規則,不至于在使用過程中發生歧義和錯誤理解。

字符型數據與開關型和數值型數據相互轉換函數主要用于各種計算過程,參加運算的必須為整型(開關型)和浮點型(數值型)的數據,一些動態展示過程也必須與數值型數據關聯,如曲線顯示

、位置移動、顏色變化、形狀大小改變等。因此,在字符型與開關型、字符型與數值型之間需要函數進行轉換,如圖2-10所示。這些函數涉及十進制與二進制、十進制與八進制、十進制與十六進制、數值與字符串的相互轉換,二進制、八進制、十六進制都是以字符串格式賦值,十進制以開關型(整型)賦值,數值以單精度浮點型賦值。歸納起來,實際上都是整型(開關型)+單精度浮點型(數值型)與字符串(字符型)之間的轉換。可參考二維碼視頻講解。

主站蜘蛛池模板: 兴业县| 绥中县| 都昌县| 永德县| 永济市| 巴彦淖尔市| 汝城县| 平安县| 若羌县| 白水县| 太湖县| 本溪市| 饶阳县| 曲麻莱县| 于田县| 白玉县| 绍兴市| 青铜峡市| 高要市| 武川县| 玛纳斯县| 华安县| 宝山区| 富蕴县| 常熟市| 定日县| 福清市| 岳阳市| 韩城市| 陵川县| 宜城市| 镇宁| 宜都市| 东乌| 盐城市| 济源市| 米泉市| 南华县| 景泰县| 泊头市| 会东县|