標籤:
一、簡單介紹
C語言的設計目標是提供一種能以簡易的方式編譯、處理低級儲存空間、產生少量的機器碼以及不需要任何運行環境支援便能啟動並執行程式設計語言。它有以下特點:簡潔緊湊、靈活方便、運算子豐富、資料類型豐富、表達方式靈活實用、允許直接存取物理地址,對硬體進行操作、產生目標代碼品質高,程式執行效率高、可移植性好、表達力強;但同時封裝性及文法嚴格限制的情況不如其他語言好。 個人認為,在進行演算法的練習和設計時,c語言是一個不錯的選擇,佔用記憶體少,更接近於底層,也很容易實現各種資料結構。
二、基礎知識
1.基本輸入輸出
scanf函數
定義在標頭檔stdio.h中,它是格式輸入函數,即按使用者指定的格式從鍵盤上把資料輸入到指定的變數之中。
函數原型:
int scanf(const char *format,...);
其調用形式為: scanf("<格式說明字串>",<變數地址>);變數地址要求有效,並且與格式說明的次序一致。
scanf()函數返回成功賦值的資料項目數,讀到檔案末尾出錯時則返回EOF。
如:
scanf("%d %d",&a,&b);
如果a和b都被成功讀入,那麼scanf的傳回值就是2。
格式說明符
轉換字元(就是%後跟的部分)
c 讀單字元
d 讀十進位整數
i 讀十進位、八進位、十六進位整數
e 讀浮點數
E 讀浮點數
f 讀浮點數
g 讀浮點數
G 讀浮點數
o 讀八位元
s 讀字串
x 讀十六進位數
X 讀十六進位數
p 讀指標值
n 至此已讀入值的等價字元數
u 讀無符號十進位整數
[ ] 掃描字元集合
% 讀 % 符號(百分比符號)
附加格式說明字元表修飾符說明
L/l 長度修飾符 輸入"長"資料
h 長度修飾符 輸入"短"資料
W 整型常數 指定輸入資料所佔寬度
* 表示本輸入項在讀入後不賦值給相應的變數
選擇性的掃描輸入例子:
#include<stdlib.h>#include<stdio.h>int main(){ int a,b,c; scanf("%d,%d,%d",a,b,c); //輸入格式為a,b,c printf("%d %d %d",a,b,c); //輸出格式為a b c(中間有空格) return 0;}
printf函數
printf()函數是格式化輸出函數, 一般用於向標準輸出裝置按規定格式輸出資訊。printf()函數的調用格式為: printf("<格式化字串>", <參量表>)。參數使用方法與scanf函數類似
2.for迴圈
編寫for迴圈時,需要注意先聲明初始變數,再在括弧內使用(與c++中不同),可採用以下形式
int i;for(i=0;i<size;i++){ // TO DO}
使用下面這種形式會出錯:
3.常用標頭檔
#include<stdlib.h> //stdlib 標頭檔即standard library標準庫標頭檔。
stdlib.h裡面定義了五種類型、一些宏和通用工具函數。 類型例如size_t、wchar_t、div_t、ldiv_t和lldiv_t; 宏例如EXIT_FAILURE、EXIT_SUCCESS、RAND_MAX和MB_CUR_MAX等等; 常用的函數如malloc()、calloc()、realloc()、free()、system()、atoi()、atol()、rand()、srand()、exit()等等。 具體的內容你自己可以開啟編譯器的include目錄裡面的stdlib.h標頭檔看看。
#include<stdio.h> // 包含了一些輸入輸出函數,如scanf,printf等
4.字串
可以用字元數組來表示字串,如
#include<stdlib.h>#include<stdio.h>int main(){ char str[30]="Hello World"; // 僅在初始化時使用 printf(str); return 0;}
可以用strcp函數來複製擷取輸入的字串
#include <stdio.h>#include <string.h>int main (){ char str1[12] = "Hello"; char str2[12] = "World"; char str3[12]; int len ; /* copy str1 into str3 */ strcpy(str3, str1); printf("strcpy( str3, str1) : %s\n", str3 ); /* concatenates str1 and str2 */ strcat( str1, str2); printf("strcat( str1, str2): %s\n", str1 ); /* total lenghth of str1 after concatenation */ len = strlen(str1); printf("strlen(str1) : %d\n", len ); return 0;}
輸出
strcpy( str3, str1) : Hellostrcat( str1, str2): HelloWorldstrlen(str1) : 10
將數字轉化為字串
a.能將整數轉換為字串而且與ANSI標準相容的方法是使用sprintf()函數
#include<stdio.h> # include <stdlib. h>void main (void);void main (void){ int num = 100; char str[25]; sprintf(str, " %d" , num); printf ("The number ‘num‘ is %d and the string ‘str‘ is %s. \n" , num, str);}
b.用fcvt()函數將浮點型值轉換為字串的一個例子:
# include <stdio. h># include <stdlib. h>void main (void);void main (void){ double num = 12345.678; char * sir; int dec_pl, sign, ndigits = 3; /* Keep 3 digits of precision. * / str = fcvt(num, ndigits, &dec-pl, &sign); /* Convert the float to a string. * / printf("Original number; %f\n" , num) ; /* Print the original floating-point value. * / printf ("Converted string; %s\n",str); /* Print the converted string‘s value. * / printf ("Decimal place: %d\n" , dec-pi) ; /* Print the location of the decimal point. * / printf ("Sign: %d\n" , sign) ; /* Print the sign. 0 = positive, 1 = negative. * /}
fcvt()函數和itoa()函數有數大的差別。fcvt()函數有4個參數:第一個參數是要轉換的浮點型值;第二個參數是轉換結果中十進位小數點右側的位元;第三個參數是指向一個整數的指標,該整數用來返迴轉換結果中十進位小數點的位置;第四個參數也是指向一個整數的指標,該整數用來返迴轉換結果的符號(0對應於正值,1對應於負值)。
5.數組,如何使用二維或高維數組,如何用它來表示矩陣,如何用它來表示圖
1、二維數組的概念
在C語言中,二維數組實際上是一種特殊的一維數組,它的每個元素也是一個一維數組。因此,二維數組下標形式正確寫法如下:int arrays[i][j]。數組元素是按照行順序儲存的,因此當按儲存順序訪問樹時,最右邊的數組下標(列)變化的最快。
2、二維數組作為函數參數
規定:如果將二維數組作為參數傳遞給函數,那麼在函數的參數聲明中必須指明數組的列數,數組的行數沒有太大關係,可以指定也可以不指定。因為函數調用時傳遞的是一個指標,它指向由行向量夠成的一維數組。因此二維數組作為函數參數正確寫法如下所示:
void Func(int array[3][10]);
void Func(int array[ ][10]);
因為數組的行數無關緊要,所以還可以寫成如下形式:
void Func(int (*array)[10]); 注意*array需要用括弧括起來。
這種形式的聲明參數是一個指標,它指向具有10個元素的一維數組。因為[]的優先順序比*的優先順序高,故*array必須用括弧括起來,否則變成了
void Func(int *array[10]);
這時候參數相當於是聲明了一個數組,該數組有10個元素,其中每個元素都是一個指向整型對象的指標。
但是不能把第二維或者更高維的大小省略,如下面的定義是不合法的:
void Func(int array[ ][ ]);
因為從實參傳遞來的是數組的起始地址,在記憶體中按數組排列規則存放(按行存放),而並不區分行和列,如果在形參中不說明列數,則系統無法決定應為多少行多 少列,不能只指定一維而不指定第二維,下面寫法是錯誤的:
void Func(int array[3][ ]);
實參數組維數可以大於形參數組,例如形參數組定義為:
void Func(int array[3][10]);
程式碼範例:
容易出現的錯誤寫法:
#include <cstdio>void print(int *arr[3]){ printf("%d\n",arr[0][0]);}int main(){ int arr[2][3] = {1,2,3,4,5,6}; print(arr); return 0;}
正確寫法:
1 #include <cstdio> 2 void print(int (*arr)[3]) //用括弧將指標括起來 3 { 4 printf("%d\n",arr[0][0]); 5 } 6 7 int main() 8 { 9 int arr[2][3] = {1,2,3,4,5,6};10 print(arr);11 return 0;12 }
6.動態分配空間問題,如何分配,是否需要指定大小
動態數組:
int *arr=(int *)malloc(size*sizeof(int)) ; //其中size是一個數值大小,你可以根據實際需要的大小而定
7.應注意與c++有哪些不同
不能在c++中編譯的c程式
7.1 在c++中,在函式宣告前調用該函數會產生編譯錯誤。但在c中,可能會正常編譯。
#include<stdio.h>int main(){ foo(); // foo() is called before its declaration/definition} int foo(){ printf("Hello"); return 0; }
7.2 在c++中,將常指標指向一個常量會產生編譯錯誤,但在c中是允許的。
#include <stdio.h> int main(void){ int const j = 20; /* The below assignment is invalid in C++, results in error In C, the compiler *may* throw a warning, but casting is implicitly allowed */ int *ptr = &j; // A normal pointer points to const printf("*ptr: %d\n", *ptr); return 0;}
7.3 在c中,void 指標可以直接賦值給其他類型指標,如int *, char *;但在c++中是不允許的。
#include <stdio.h>int main(){ void *vptr; int *iptr = vptr; //In C++, it must be replaced with int *iptr=(int *)vptr; return 0;}
7.4 在c++中常量必須要被初始化,但在c中是可選的。
#include <stdio.h>int main(){ const int a; // LINE 4 return 0;}
7.5 c++特定的關鍵字在c中是允許的。雖然這樣,但實際編程過程中,應盡量避免這些問題。
#include <stdio.h>int main(void){ int new = 5; // new is a keyword in C++, but not in C printf("%d", new);}
7.6 c++有更嚴格的類型檢查。例如,下面的程式在c中可以通過,但不能在c++中編譯。
#include <stdio.h>int main(){ char *c = 333; printf("c = %u", c); return 0;}
熟悉c語言(簡單入門)