Vi 文本編輯器
《Vi 文本編輯器》由會員分享,可在線閱讀,更多相關(guān)《Vi 文本編輯器(6頁珍藏版)》請在裝配圖網(wǎng)上搜索。
1、Vi 文本編輯器 1. 實驗?zāi)康? 1. 了解和掌握使用Vi編輯器編輯文件 2. 了解和掌握使用gcc編譯器和gdb調(diào)試器 3. 對程序編譯運行,分析運行結(jié)果。 2. 實驗原理和實驗設(shè)備 Linux 操作系統(tǒng) 3. 實驗步驟 1. 如何調(diào)用vi文本編輯器,使用gcc編譯器和gdb調(diào)試器,編譯運行文件,分析運行結(jié) 果。 進入 VI 編輯器 格式:vi文件名 例 : vi sy.c Vi 編輯器三種工作方式: 1.編輯方式:進入 VI 處于編輯方式 2. 文本輸入方式:在編輯方式下輸入a ,進入追加方式,輸入i,進入插入方式 3. 命令方式:在輸入方式下,按 Esc
2、鍵,由文本輸入轉(zhuǎn)向編輯方式,輸入冒號:進入命 令方式
4. 退出 vi
: wq 寫文件退出
: w wenjianming 寫文件
: q! 不寫退出
: wq! 寫退出
編譯 c 文件
Gcc -o wenjianming.out wenjianming.c
運行文件:
./wenjianming.out
2. 程序示例
(1) /* 父子進程之間的同步之例 */
#include
3、ork() 返回值:0創(chuàng)建成功,從子進程返回; >0創(chuàng)建成功,從父進程返回,其值為子進程的PID號; -1創(chuàng)建失敗。*/ { if (fork()) /*create the child2*/ {printf (“parent's context.\n");/*輸出字符串"parent's context”.*/ printf(“parent is waiting the child1 terminate.\n); wait(O);/*在父進程中需要等待子進程結(jié)束處使用系統(tǒng)調(diào)用wait(O)。*/ printf(“parent is waiting the child2 ter
4、minate.\n”); wait(0); printf(“parent terminate.\n”); exit(0); } else /* child2*/ printf(“child2's context.\n"); sleep(5);/*使用 sleep(5)延時 5 秒*/ printf(“ child2 terminate.\n”); exit(O);/*在子進程結(jié)束處使用系統(tǒng)調(diào)用exit(),使子進程自我終止,并向該父進程發(fā)終止 信號;*/ } else { if(pid1==0)/* child1 */ { printf(“child1's conte
5、xt.\n”); sleep(10); printf(“child1 terminate.\n”); exit(0); } } } 分析: 上述程序是父進程首先創(chuàng)建一個子進程,若成功,再創(chuàng)建另一個子進程,之后三個 進程并發(fā)執(zhí)行。究竟誰先執(zhí)行,是隨機的,可根據(jù)執(zhí)行結(jié)果判斷。試分析該程序的所有運行 結(jié)果。 注釋: fork( ) 調(diào)用正確完成時,給父進程返回地是被創(chuàng)建子進程的標識,給子進程返回 的是 0;創(chuàng)建失敗時,返回給父進程的時-1; exit(0) 進程終止自己 wait(0) 父進程同步等待子進程結(jié)束,即無子進程結(jié)束,父進程等待。 (2) 管道通信機制 通過使用管道實
6、現(xiàn)兩個和多個進程之間的通信。所謂管道,就是將一個進程的標準輸 出與另一個進程的標準輸入聯(lián)系在一起,進行通信的一種方法。同組進程之間可用無名管道 進行通信,不同組進程可通過有名管道通信。
使用無名管道進行父子進程之間的通信
#include
7、; pipe(chan1); pid=fork(); if(pid<0) { printf(“to create child error\n”); exit(1); } if(pid>0) { close(chan1[0]); /*父進程關(guān)閉讀通道*/ printf(“parent process sends a message to child.\n”); write(chan1[1],parent,sizeof(parent)); close(chan1[1]); printf(“parent process waits the child to terminate.\n”
8、); wait(0); printf(“parent process terminates.\n”); } else{ close(chanl[l]);/*子進程關(guān)閉寫通道*/ read(chan1[0],buf,100); printf(“the message read by child process form parent is %s.\n”,buf); close (chanl[0]); printf(“child process terminates\n”); } } 觀察運行結(jié)果。 注釋:pipe( int filedes[2]):創(chuàng)建一個無名管道,filedes
9、[0]為讀通道,filedes[1]為寫通道。 (3)Linux 中的多線程編程 threads.c
#include
10、 for (i = 0; i < MAX; i++) { printf("thread1 : number = %d\n",number); pthread_mutex_lock(&mut); number++; pthread_mutex_unlock(&mut); sleep(2); } printf("threadl :主函數(shù)在等我完成任務(wù)嗎? \n"); pthread_exit(NULL); } void *thread2() { printf("thread2 : I'm thread 2\n"); for (i = 0; i < MAX; i++) {
11、 printf("thread2 : number = %d\n",number); pthread_mutex_lock(&mut); number++; pthread_mutex_unlock(&mut); sleep(3); } printf("thread2 :主函數(shù)在等我完成任務(wù)嗎? \n"); pthread_exit(NULL); } void thread_create(void) { int temp; memset(&thread, 0, sizeof(thread)); //commentl /*創(chuàng)建線程*/ if((temp = pthread
12、_create(&thread[0], NULL, threadl, NULL)) != 0) //comment2 prin tf("線程1創(chuàng)建失敗!\n"); else prin tf("線程1被創(chuàng)建\n"); if((temp = pthread_create(&thread[1], NULL, thread2, NULL)) != 0) //comment3 printf ("線程2創(chuàng)建失敗"); else printf("線程2被創(chuàng)建\n"); } void thread_wait(void) { /*等待線程結(jié)束*/ if(thread[0] !=0) { /
13、/comment4 pthread_join(thread[0],NULL); prin tf("線程1已經(jīng)結(jié)束\n"); } if(thread[1] !=0) { //comment5 pthread_join(thread[1],NULL); printf ("線程2已經(jīng)結(jié)束\n"); } } int main() { /*用默認屬性初始化互斥鎖*/ pthread_mutex_init(&mut,NULL); prin tf("我是主函數(shù)哦,我正在創(chuàng)建線程,呵呵\n"); thread_create(); prin tf( 〃我是主函數(shù)哦,我正在等待線程完成任務(wù)阿,
14、呵呵\『); thread_wait(); return 0; } 3. 注意:Gcc - lpthread - o thread.out thread.c 線程相關(guān)操作 1) pthread_t pthread_t 在頭文件/usr/include/bits/pthreadtypes.h 中定義: typedef unsigned long int pthread_t; 它是一個線程的標識符。 2) pthread_create 函數(shù) pthread_create 用來創(chuàng)建一個線程,它的原型為: extern int pthread_create __P ((pthre
15、ad_t *__thread, __const pthread_attr_t *__attr, void *(*__start_routine) (void *), void *__arg)); 第一個參數(shù)為指向線程標識符的指針,第二個參數(shù)用來設(shè)置線程屬性,第三個參數(shù)是 線程運行函數(shù)的起始地址,最后一個參數(shù)是運行函數(shù)的參數(shù)。這里,我們的函數(shù)thread 不需要參數(shù),所以最后一個參數(shù)設(shè)為空指針。第二個參數(shù)我們也設(shè)為空指針,這樣將生 成默認屬性的線程。對線程屬性的設(shè)定和修改我們將在下一節(jié)闡述。當(dāng)創(chuàng)建線程成功時, 函數(shù)返回0若不為0則說明創(chuàng)建線程失敗,常見的錯誤返回代碼為EAGAIN和EINVAL
16、。 前者表示系統(tǒng)限制創(chuàng)建新的線程,例如線程數(shù)目過多了;后者表示第二個參數(shù)代表的線 程屬性值非法。創(chuàng)建線程成功后,新創(chuàng)建的線程則運行參數(shù)三和參數(shù)四確定的函數(shù),原 來的線程則繼續(xù)運行下一行代碼。 3) pthread_join pthread_exit 函數(shù) pthread_join 用來等待一個線程的結(jié)束。函數(shù)原型為: extern int pthread_join __P ((pthread_t __th, void **__thread_return)); 第一個參數(shù)為被等待的線程標識符,第二個參數(shù)為一個用戶定義的指針,它可以用來存 儲被等待線程的返回值。這個函數(shù)是一個線程阻塞的函數(shù)
17、,調(diào)用它的函數(shù)將一直等待到 被等待的線程結(jié)束為止,當(dāng)函數(shù)返回時,被等待線程的資源被收回。一個線程的結(jié)束有 兩種途徑,一種是象我們上面的例子一樣,函數(shù)結(jié)束了,調(diào)用它的線程也就結(jié)束了;另 一種方式是通過函數(shù) pthread_exit 來實現(xiàn)。它的函數(shù)原型為: extern void pthread_exit __P ((void *__retval)) __attribute__ ((__noreturn__)); 唯一的參數(shù)是函數(shù)的返回代碼,只要 pthread_join 中的第二個參數(shù) thread_return 不是 NULL,這個值將被傳遞給thread_return。最后要說明的是,一個
18、線程不能被多個線程 等待,否則第一個接收到信號的線程成功返回,其余調(diào)用pthread_join的線程則返回錯 誤代碼 ESRCH。 在這一節(jié)里,我們編寫了一個最簡單的線程,并掌握了最常用的三個函數(shù)pthread_create, pthread_join和pthread_exit。下面,我們來了解線程的一些常用屬性以及如何設(shè)置這些 屬性。 互斥鎖相關(guān) 互斥鎖用來保證一段時間內(nèi)只有一個線程在執(zhí)行一段代碼。 1) pthread_mutex_init 函數(shù)pthread_mutex_init用來生成一個互斥鎖。NULL參數(shù)表明使用默認屬性。如果 需要聲明特定屬性的互斥鎖, 須調(diào)用函數(shù) pth
19、read_mutexattr_init 。 函數(shù) pthread_mutexattr_setpshared 和函數(shù) pthread_mutexattr_settype 用來設(shè)置互斥鎖屬性。前 一個函數(shù)設(shè)置屬性 pshared,它有兩個取值, PTHREAD_PROCESS_PRIVATE和 PTHREAD_PROCESS_SHARED。前者用來不同進程中的線程同步,后者用于同步本進 程的不同線程。在上面的例子中,我們使用的是默認屬性 PTHREAD_PROCESS_ PRIVATE。后者用來設(shè)置互斥鎖類型,可選的類型有PTHREAD_MUTEX_NORMAL、 PTHREAD_MUTEX_ER
20、RORCHECK、PTHREAD_MUTEX_RECURSIVE 和 PTHREAD _MUTEX_DEFAULT。它們分別定義了不同的上鎖、解鎖機制,一般情況下,選用最后 一個默認屬性。 2) pthread_mutex_lock pthread_mutex_unlock pthread_delay_np pthread_mutex」ock聲明開始用互斥鎖上鎖,此后的代碼直至調(diào)用pthread_mutex_unlock 為止, 均被上鎖, 即同一時間只能被一個線程調(diào)用執(zhí)行。 當(dāng)一個線程執(zhí)行到 pthread_mutex_lock 處時,如果該鎖此時被另一個線程使用,那此線程被阻塞,即程序
21、 將等待到另一個線程釋放此互斥鎖。 注意: 1) 需要說明的是,上面的兩處sleep不光是為了演示的需要,也是為了讓線程睡眠一段 時間,讓線程釋放互斥鎖,等待另一個線程使用此鎖。 2) 請千萬要注意里頭的注釋comment1-5,如果沒有comment】和comment4,comment5, 將導(dǎo)致在pthread_join的時候出現(xiàn)段錯誤,另外,上面的comment2和comment3是根源 所在,所以千萬要記得寫全代碼。因為上面的線程可能沒有創(chuàng)建成功,導(dǎo)致下面不可能 等到那個線程結(jié)束,而在用 pthread_join 的時候出現(xiàn)段錯誤(訪問了未知的內(nèi)存區(qū))。 另外,在使用memset
22、的時候,需要包含string.h頭文件。 實驗報告 (1) 實驗題目。 (2) 說明對程序的理解,程序后加上注釋語句。 (3) 分析程序的執(zhí)行結(jié)果并加以解釋。 4. 實驗結(jié)果分析 vi是“ Visual in terface ”的簡稱,它可以執(zhí)行輸出、刪除、查找、替換、塊操作等 眾多文本操作,而且用戶可以根據(jù)自己的需要對其進行定制,這是其他編輯程序所沒有的。 vi不是一個排版程序,它不像Word或WPS那樣可以對字體、格式、段落等其他屬性進 行編排,它只是一個文本編輯程序。 Vi 是全屏幕文本編輯器,它沒有菜單,只有命令。 5. 實驗小結(jié) 文本編輯器有很多,比如圖形模式的 gedit、 kwrite、 OpenOffice ... ... ,文本模 式下的編輯器有vi、vim (vi的增強版本)和nano vi和vim是我們在Linux中最 常用的編輯器。掌握vi(vim)最簡單的用法,以讓我們作為Linux入門級用戶在最短的時 間內(nèi)學(xué)會使用它。
- 溫馨提示:
1: 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
2: 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
3.本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
5. 裝配圖網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責(zé)。
6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 川渝旅游日記成都重慶城市介紹推薦景點美食推薦
- XX國有企業(yè)黨委書記個人述責(zé)述廉報告及2025年重點工作計劃
- 世界濕地日濕地的含義及價值
- 20XX年春節(jié)節(jié)后復(fù)工安全生產(chǎn)培訓(xùn)人到場心到崗
- 大唐女子圖鑒唐朝服飾之美器物之美繪畫之美生活之美
- 節(jié)后開工第一課輕松掌握各要點節(jié)后常見的八大危險
- 廈門城市旅游介紹廈門景點介紹廈門美食展示
- 節(jié)后開工第一課復(fù)工復(fù)產(chǎn)十注意節(jié)后復(fù)工十檢查
- 傳統(tǒng)文化百善孝為先孝道培訓(xùn)
- 深圳城市旅游介紹景點推薦美食探索
- 節(jié)后復(fù)工安全生產(chǎn)培訓(xùn)勿忘安全本心人人講安全個個會應(yīng)急
- 預(yù)防性維修管理
- 常見閥門類型及特點
- 設(shè)備預(yù)防性維修
- 2.乳化液泵工理論考試試題含答案