日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

循环队列及C语言实现二

發(fā)布時間:2023/12/9 编程问答 35 豆豆
生活随笔 收集整理的這篇文章主要介紹了 循环队列及C语言实现二 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

  在我的上一篇博文中已經(jīng)講到循環(huán)隊列的特點作用以及C語言實現(xiàn),當(dāng)然實現(xiàn)和操作的方式比較簡單,在實際項目應(yīng)用中略顯粗糙。因此,這一篇提供一個進階篇的實現(xiàn)與操作接口。具體函數(shù)作用可以參見我的注釋部分,使用的時候直接把里面的接口函數(shù)放在一個頭文件里面直接調(diào)用就可以啦,十分方便易用,但是可以實現(xiàn)的功能不可小覷哦,比如我在寫高速USB設(shè)備驅(qū)動(20MB/s)以及網(wǎng)絡(luò)抓包緩存的時候用到的都是這個看似簡單的數(shù)據(jù)結(jié)構(gòu),所以還沒有熟練運用的要加把勁了。需要注意的地方包括:

<1> 不再利用上一篇中 “q->front = (q->rear + 1) % q->size” 的關(guān)系來進行隊列空還是滿的判斷了,這次利用 space 剩余緩存空間大小來判斷。

<2> 寫緩沖區(qū)的時候,要進行緩沖區(qū)剩余空間大小 space 的判斷,如果要寫入空間小于等于剩余空間,那么就可以將數(shù)據(jù)完全寫入緩沖區(qū),此時寫入長度等于要寫入的數(shù)據(jù)長度,否則只能將部分數(shù)據(jù)寫入緩沖區(qū),返回長度就等于剩余空間大小了。

<3> 讀緩沖區(qū)同理,要進行當(dāng)前緩沖區(qū)中可用緩存的大小的判斷,也即已寫入緩存大小的判斷。若要讀出的數(shù)據(jù)長度小于已寫入緩存,那么返回長度為希望讀出的數(shù)據(jù)長度,否則為已寫入緩存的長度。

<4> 在寫入和讀出的時候尤其需要注意到達緩沖區(qū)邊界的時候,數(shù)據(jù)和讀寫位置的處理。如果讀寫到了邊界,那么就要分兩次讀取了,另外讀寫位置一定不能超越分配的緩沖區(qū)邊界,所以在循環(huán)隊列中數(shù)據(jù)的讀寫位置前移的時候都要對緩沖區(qū)長度取余以保證數(shù)據(jù)操作的安全性。

  下面就是代碼部分了,若有不明或不妥之處,可以直接 send comments to me :-D

/** Queue operation API - 1.0** Copyright (C) 2016 SoldierJazz (SoldierJazz@163.com)** This program is free software; you can redistribute it and/or* modify it. **/#include <stdio.h> #include <stdlib.h> #include <string.h>/*** Queue - queue structure* @buf: queue buffer* @read: position of read* @write: position of write* @size: buffer size* @space: writable buffer size*/ typedef struct {char *buf;unsigned int read;unsigned int write;unsigned int size;unsigned int space; } Queue;#define Avail(q) (q->size - q->space)/*** Queue_Init - init a queue* @q: pointer of queue* @size: size of buffer in queue** Must be called when started. */ void Queue_Init(Queue *q, int size) {q->buf = (char *)malloc(sizeof(char) * size);q->read = 0;q->write = 0;q->size = size;q->space = size; }/*** Queue_Destroy - destroy a queue* @q: pointer of queue*/ void Queue_Destroy(Queue *q) {free(q->buf); }/*** Queue_Empty - tests whether a queue is empty* @q: the queue to test*/ bool Queue_Empty(Queue *q) {return (q->space == q->size); }/*** Queue_Full - tests whether a queue is full* @q: the queue to test*/ bool Queue_Full(Queue *q) {return (q->space == 0); }/*** AddQueue - add a byte to queue* @q: the queue to add to* @val: the char to add*/ bool AddQueue(Queue *q, char val) {if (!Queue_Full(q)) {q->buf[q->write] = val;q->write = (q->write + 1) % q->size;q->space--;return true;} return false; }/*** DelQueue - delete a byte from queue* @q: the queue to delete from* @val: the char deleted*/ bool DelQueue(Queue *q, char *val) {if (!Queue_Empty(q)) {*val = q->buf[q->read];q->read = (q->read + 1) % q->size;q->space++;return true;}return false; }/*** WriteQueue - write buffers to queue* @q: the queue to write in* @buf: pointer of write buffer* @len: length of write buffer*/ static int WriteQueue(Queue *q, char *buf, unsigned int len) {unsigned int ret = 0;unsigned int rest = q->size - q->write;if (!Queue_Full(q)) {if (q->space >= len) {ret = len;if (rest >= len) {memcpy(q->buf + q->write, buf, len);q->write = (q->write + len) % q->size;q->space -= len;} else {memcpy(q->buf + q->write, buf, rest);q->write = 0;memcpy(q->buf, buf + rest, len - rest);q->write = len -rest;q->space -= len;}} else {ret = q->space;if (rest >= q->space) {memcpy(q->buf + q->write, buf, q->space);q->write = (q->write + q->space) % q->size;q->space = 0;} else {memcpy(q->buf + q->write, buf, rest);q->write = 0;memcpy(q->buf, buf + rest, q->space - rest);q->write = q->space -rest;q->space = 0;}} } return ret; }/*** ReadQueue - read buffers from queue* @q: the queue to read from* @buf: pointer of read buffer* @len: read length*/ static int ReadQueue(Queue *q, char *buf, unsigned int len) {unsigned int rest = q->size - q->read;unsigned int ret = 0;if (!Queue_Empty(q)) {if (Avail(q) >= len) {ret = len;if (rest >= len) {memcpy(buf, q->buf + q->read, len);q->read = (q->read + len) % q->size;q->space += len;} else {memcpy(buf, q->buf + q->read, rest);q->read = 0;memcpy(buf + rest, q->buf, len - rest);q->read = len -rest;q->space += len;}return len;} else {ret = Avail(q);if (rest >= Avail(q)) {memcpy(buf, q->buf + q->read, Avail(q));q->read = (q->read + Avail(q)) % q->size;q->space = q->size;} else {memcpy(buf, q->buf + q->read, rest);q->read = 0;memcpy(buf + rest, q->buf, Avail(q) - rest);q->read = Avail(q) -rest;q->space = q->size;}}} return ret; }void main() {int ret = 0;char buf[10] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};char buf2[10];Queue q;Queue_Init(&q, 10);ret = WriteQueue(&q, buf, 5);printf("writed %d bytes.\n", ret);ret = ReadQueue(&q, buf2, 2);printf("readed %d bytes.\n", ret);ret = WriteQueue(&q, buf, 10);printf("writed %d bytes.\n", ret);ret = ReadQueue(&q, buf2, 7);printf("readed %d bytes.\n", ret);ret = ReadQueue(&q, buf2, 7);printf("readed %d bytes.\n", ret);Queue_Destroy(&q); }

運行結(jié)果如下:


關(guān)于循環(huán)隊列主題的系列文章,可移步至以下鏈接:
1. 《循環(huán)隊列及C語言實現(xiàn)<一>》
2. 《循環(huán)隊列及C語言實現(xiàn)<二>》
3. 《循環(huán)隊列及C語言實現(xiàn)<三>》

總結(jié)

以上是生活随笔為你收集整理的循环队列及C语言实现二的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。