循环队列中,由于入队时尾指针向前追赶头指针;出队时头指针向前追赶尾指针,造成队空和队满时头尾指针均相等。因此,无法通过条件front==rear来判别队列是"空"还是"满"。使用求余运算可以判断队列是否已满。
代码
//circular Queue 循环队列实现 #include <stdlib.h>#include <stdio.h>#define MAXSIZE 100typedef int ElemType typedef struct { ElemType *base//存储内存分配基地址 int front //队列头索引 int rear //队列尾索引}circularQueue//初始化队列InitQueue(circularQueue *q){ q->base = (ElemType *)malloc((MAXSIZE) * sizeof(ElemType))if (!q->base) exit(0)q->front = q->rear = 0} //入队列 *** 作InsertQueue(circularQueue *q, ElemType e){ if ((q->rear + 1) % MAXSIZE == q->front) return//队列已满时,不执行入队 *** 作 q->base[q->rear] = e //将元素放入队列尾部 q->rear = (q->rear + 1) % MAXSIZE//尾部元素指向下一个空间位置,取模运算保证了索引不越界(余数一定小于除数)} //出队列 *** 作DeleteQueue(circularQueue *q, ElemType *e){ if (q->front == q->rear) return //空队列,直接返回 *e = q->base[q->front] //头部元素出队 q->front = (q->front + 1) % MAXSIZE}
更多信息可以参考《Linux就该这么学》
Linux认证题目含答案
Linux是一套免费使用和自由传播的类Unix *** 作系统,是一个基于POSIX和UNIX的多用户、多任务、支持多线程和多CPU的 *** 作系统。以下是我整理的关于Linux认证题目含答案,希望大家认真阅读!
1.使用vi编辑文本只读时,强制存盘并退出的命令是?(单选题)
A :w! B :q! C :wq! D :e!
答案:C
2.使用什么命令把两个文件的合并成一个文件?(单选题)
A cat B grep Cawk D cut
答案:A
3以下哪一个命令只查找源代码、二进制文件和帮助文件,而不是所以类型的文件?此命令查找的目录是由环境变量$PATH指定的。(单选题)
A whereis B whatis C which D apropos
答案:A
4.使用什么命令进行查询,并不真正对硬盘上的文件系统进行查找,而是对文件名数据库进行检索,而且可以使用通配符?和*?(单选题)
A whereis B find C locate D type
答案:C
5.使用什么命令把打印任务放到打印队列中去打印。(单选题)
A lprm B lpq C lpd D lpr
答案:D
6、使用什么命令自动卸载已安装的老版本软件包并安装新软件包,即使不存在老版本也会安装新软件包。(单选题)
A:rpm -U B:rpm -i C: rpm -F D: rpm -e
答案:A
7、如果文件/usr/bin/passwd的属性为-r-s - -x- -x,则s代表?(单选题)
A:SUID B: SGID C: Sticky D:Excutable
答案:A
8、当一个文件属性为drwxrwxrwt,则这个文件的权限是什么样的?(多选题)
A: 任何用户皆可读取、可写入 B:root 可以删除该目录的文件
C:给普通用户以文件所有者的特权 D:文件拥有者有权删除该目录的文件
答案:ABD
9:什么命令用来查看硬盘被占用了多少空间和剩余多少空间?(单选题)
A: du B: df C: free D: vmstat
答案:B
10: Linux 使用者的帐号、密码与群组的名称文件放在哪些文件里?(多选题)
A:/etc/passwd B: /etc/shadow
C: /etc/group D: /etc/users
答案:ABC
11、暂停某用户帐号可以使用如下哪些方法?(多选题)
A.把/etc/passwd文件中该用户信息字段前加#
B.passwd -1[用户名]
C.将/etc/passwd该用户信息shell字段改成/sbin/nologin
D.passwd -u[用户名]
答案:BC
12、什么命令可以查看曾经登录到此系统的用户清单?(*单选题)
A.ps B.last C.lastcomm D.accton
答案:B
13、以下哪一个内核版本属于测试版本?(单选题)
A.2.0.0 B.1.2.25 C 2.3.4 D 3.0.13
答案:C
14、假如你已经把编译好的新内核复制到/boot目录,如果你想让系统启动时缺省使用新内核而旧的内核依然有效,你需要在/etc/lilo.conf文件中添加哪一个选项?(单选)
A.boot=B.image= C.install= D.map=
答案:B
15、编译内核时,可以使用哪些命令对内核进行配置?(多选)
A.makeconfig B.make menuconfig C.make oldconfig D. makexconfig
答案:ABCD
16.假如系统启动进入运行级别3,则在/etc/rc.d/rc3.d/目录中,以下哪一个脚本首先执行?(单选题)
A.K20rwhod B. S30syslog C. K96pcmcia D. S99linuxcof
答案:B
17.假如你想计划让系统自动在每个月的第一天早上4点钟执行一个维护工作,以下哪个cron是正确的?(单选题)
A.00 4 1 # * /maintenance.pl B. 4 1 * *~/maintenance.pl
C.0 4 31 /1 * * ~/maintenance.pl D. 1 4 00 ~/maintenance.pl
答案:A
18在/etc/fstab指定的文件系统加载参数中,什么参数一般用于CD-ROM等移动设备?(单选题)
A.defaults B. sw C. rw和ro D. noauto
答案:D
19终止一个前台进程可能用到的'命令和 *** 作是?(单选题)
A.kill B. <CTRL>+C C. shut down D. halt
答案:B
20一个文件名为rr.Z,可以用来解压缩的命令是?(单选题)
A.tar B. gzip C. compress D. uncompress
答案:D
21、在Linux中,如何标识接在IDE0上的slave硬盘的第2个扩展分区?(C)
A. /dev/hdb2
B. /dev/hd1b2
C. /dev/hdb6
D. /dev/hd1b6
22、在应用程序起动时,如何设置进程的优先级?(B)
A. priority
B. nice
C. renice
D. setpri
23、在 bash 中, 在一条命令后加入 "1>&2" 意味着:(C)
A. 标准错误输出重定向到标准输入
B. 标准输入重定向到标准错误输出
C. 标准输出重定向到标准错误输出
D. 标准输出重定向到标准输入
24、下面哪条命令可以把f1.txt复制为f2.txt?(C)
A. cp f1.txt | f2.txt
B. cat f1.txt | f2.txt
C. cat f1.txt >f2.txt
D. copy f1.txt | f2.txt
25、显示一个文件最后几行的命令是:(D)
A. tac
B. tail
C. rear
D. last
26、如何快速切换到用户John的主目录下?(D)
A. cd @John
B. cd #John
C. cd &John
D. cd ~John
27、把一个流中所有字符转换成大写字符,可以使用下面哪个命令?(A)
A. tr a-z A-Z
B. tac a-z A-Z
C. sed /a-z/A-Z
D. sed --toupper
28、使用什么命令可以查看Linux的启动信息?(B)
A. mesg -d
B. dmesg
C. cat /etc/mesg
D. cat /var/mesg
29、运行级定义在:(B)
A. in the kernel
B. in /etc/inittab
C. in /etc/runlevels
D. using the rl command
30、如何装载(mount)上在 /etc/fstab 文件中定义的所有文件系统?(A)
A. mount -a
B. mount /mnt/*
C. mount
D. cat /etc/fstab | mount
31、如果使用ln命令将生成了一个指向文件old的符号链接new,如果你将文件old删除,是否还能够访问文件中的数据?(A)
A. 不可能再访问
B. 仍然可以访问
C. 能否访问取决于file2的所有者
D. 能否访问取决于file2的权限
32、在ext2fs文件系统中,缺省的为root用户保留多大的空间?(C)
A. 3%
B. 5%
C. 10%
D. 15%
33、下面哪个命令用来显示系统中各个分区中inode的使用情况?(A)
A. df -i
B. df -H
C. free -b
D. du -a -c /
34、在大多数Linux发行版本中,图形方式的运行级定义为?(D)
A. 1
B. 2
C. 3
D. 5
35、如何在系统文档中找到关于print这个单词的所有说明?(D)
A. man print
B. which print
C. locate print
D. apropos print
36、命令 man 5 passwd 含义是?(B)
A. 显示 passwd 命令的使用方法
B. 显示 passwd 文件的结构
C. 显示 passwd 命令的说明的前五行
D. 显示关于passwd的前五处说明文档。
37、如何在文件中查找显示所有以"*"打头的行?(D)
A. find * file
B. wc -l * C. grep -n * file
D. grep * file
38、在ps命令什么参数是用来显示所有用户的进程的?(A)
A. a
B. b
C. u
D. x
39、显示二进制文件的命令是?(A)
A. od
B. vil
C. view
D. binview
40、如何显示Linux系统中注册的用户数(包含系统用户)?(D)
A. account -l
B. nl /etc/passwd |head
C. wc --users /etc/passwd
D. wc --lines /etc/passwd
41、在一行结束位置加上什么符号,表示未结束,下一行继续?(B)
A. /
B.
C.
D. |
42、命令 kill 9 的含义是:(D)
A. kills the process whose PID is 9.
B. kills all processes belonging to UID 9.
C. sends SIGKILL to the process whose PID is 9.
D. sends SIGTERM to the process whose PID IS 9.
43、如何删除一个非空子目录/tmp?(D)
A. del /tmp/*
B. rm -rf /tmp
C. rm -Ra /tmp/*
D. rm -rf /tmp/*
44、使用什么命令可以在今天午夜运行命令 cmd1 ?(D)
A. at midnight cmd1
B. cron -at "00:00" cmd1
C. batch -t "00:00" D. echo "cmd1" | at midnight
45、你的系统使用增量备份策略,当需要恢复系统时,你需要按什么顺序恢复备份数据?(B)
A. 最后一次全备份,然后从最早到最近的增量备份
B. 最后一次全备份,然后从最近到最早的增量备份
C. 最早到最近的增量备份,然后最后一次全备份
D. 最近到最早的增量备份,然后最后一次全备份
46、对所有用户的变量设置,应当放在哪个文件下?(D)
A. /etc/bashrc
B. /etc/profile
C. ~/.bash_profile
D. /etc/skel/.bashrc
47、Linux系统中,一般把命令 ls 定义为 ls --color 的别名,以便以不同颜色来标识不同类型的文件。但是,如何能够使用原先的ls命令?
(A)
A. ls
B. ls
C. ls $$
D. ls --noalias
48、在Linux系统中的脚本文件一般以什么开头?(D)
A. $/bin/sh
B. #!/bin/sh
C. use /bin/sh
D. set shell=/bin/sh
49、下面哪种写法表示如果cmd1成功执行,则执行cmd2命令?(A)
A. cmd1&&cmd2
B. cmd1|cmd2
C. cmd1cmd2
D. cmd1||cmd2
50、在哪个文件中定义网卡的I/O地址?(C)
A. cat /proc/modules
B. cat /proc/devices
C. cat /proc/ioports
D. cat /io/dma
因为不仅仅信号量,共享内存、消息队列在NDK下都不能用,所以之前使用Linux 下IPC的消息队列,msgget/msgsnd/msgrcv都不能使用,所以没有办法,只能自己实现消息队列,采用linux 下互斥锁和条件变量实现了读时-队列空-会阻塞,写时-队列满-会阻塞。
talk is easy, show me the code. -- 废话少说,放码过来。编译时候使用 cc main.c -pthread,注意-pthread参数,因为依赖线程库。
########################################################################
#include <stdio.h>
#include <pthread.h>
#include <string.h>
#include <stdlib.h>
#include<sys/time.h>
#define MAX_QUEUE_SIZE_IN_BYTES (1024)
#define MQ_SIZE_MAX 512
#define MQ_LENGTH_MAX 30
#define MQ_NAME "msg queue example"
typedef struct _simple_queue
{
int front
int rear
int length
int queue_type
pthread_mutex_t data_mutex
pthread_cond_t data_cond
int write_pos
char queue_name[32]
void *data[0]
}simple_queue
typedef enum _queue_type
{
QUEUE_BLOCK = 0,
QUEUE_NO_BLOCK,
}queue_type
typedef enum _queue_status
{
QUEUE_IS_NORMAL = 0,
QUEUE_NO_EXIST,
QUEUE_IS_FULL,
QUEUE_IS_EMPTY,
}queue_status
typedef enum _cntl_queue_ret
{
CNTL_QUEUE_SUCCESS = 0,
CNTL_QUEUE_FAIL,
CNTL_QUEUE_TIMEOUT,
CNTL_QUEUE_PARAM_ERROR,
}cntl_queue_ret
typedef enum _queue_flag
{
IPC_BLOCK = 0,
IPC_NOWAIT = 1,
IPC_NOERROR = 2,
}queue_flag
typedef struct _simple_queue_buf
{
int msg_type
char msg_buf[50]
}queue_buf
simple_queue* create_simple_queue(const char* queue_name, int queue_length, int queue_type)
{
simple_queue *this = NULL
if (NULL == queue_name || 0 == queue_length)
{
printf("[%s] param is error\n", __FUNCTION__)
return NULL
}
if(queue_length >MAX_QUEUE_SIZE_IN_BYTES)
{
printf("[%s] param is error,queue_length should less than %d bytes\n", __FUNCTION__, MAX_QUEUE_SIZE_IN_BYTES)
return NULL
}
this = (simple_queue*)malloc(sizeof(simple_queue) + queue_length * sizeof(void*))
if (NULL != this)
{
this->front = 0
this->rear = 0
this->length = queue_length
this->queue_type = queue_type
if (0 != pthread_mutex_init(&(this->data_mutex), NULL) || 0 != pthread_cond_init(&(this->data_cond), NULL))
{
printf("[%s]pthread_mutex_init failed!\n", __FUNCTION__)
free(this)
this = NULL
return NULL
}
strcpy(this->queue_name, queue_name)
}
else
{
printf("[%s]malloc is failed!\n", __FUNCTION__)
return NULL
}
return this
}
queue_status is_full_queue(simple_queue* p_queue)
{
queue_status ret = QUEUE_IS_NORMAL
do
{
if (NULL == p_queue)
{
printf("[%s] param is error\n", __FUNCTION__)
ret = QUEUE_NO_EXIST
break
}
if (p_queue->front == ((p_queue->rear + 1) % (p_queue->length)))
{
printf("[%s] queue is full\n", __FUNCTION__)
ret = QUEUE_IS_FULL
break
}
}while(0)
return ret
}
queue_status is_empty_queue(simple_queue* p_queue)
{
queue_status ret = QUEUE_IS_NORMAL
do
{
if (NULL == p_queue)
{
printf("[%s] param is error\n", __FUNCTION__)
ret = QUEUE_NO_EXIST
break
}
if (p_queue->front == p_queue->rear)
{
printf("[%s] queue is empty\n", __FUNCTION__)
ret = QUEUE_IS_EMPTY
break
}
}while(0)
return ret
}
cntl_queue_ret push_simple_queue(simple_queue* p_queue, void* data, queue_flag flg)
{
int w_cursor = 0
if(NULL == p_queue || NULL == data)
{
printf("[%s] param is error\n", __FUNCTION__)
return CNTL_QUEUE_PARAM_ERROR
}
pthread_mutex_lock(&(p_queue->data_mutex))
w_cursor = (p_queue->rear + 1)%p_queue->length
if (w_cursor == p_queue->front)
{
if(flg == IPC_BLOCK)
{
pthread_cond_wait(&(p_queue->data_cond), &(p_queue->data_mutex))
}
else
{
printf("[%s]: queue is full\n", __FUNCTION__)
pthread_mutex_unlock(&(p_queue->data_mutex))
return CNTL_QUEUE_FAIL
}
w_cursor = (p_queue->rear + 1)%p_queue->length
}
p_queue->data[p_queue->rear] = data
p_queue->rear = w_cursor
pthread_mutex_unlock(&(p_queue->data_mutex))
pthread_cond_signal(&(p_queue->data_cond))
return CNTL_QUEUE_SUCCESS
}
cntl_queue_ret pop_simple_queue(simple_queue* p_queue, void** data, queue_flag flg)
{
if(NULL == p_queue)
{
printf("[%s] param is error\n", __FUNCTION__)
return CNTL_QUEUE_PARAM_ERROR
}
pthread_mutex_lock(&(p_queue->data_mutex))
if (p_queue->front == p_queue->rear)
{
if(flg == IPC_BLOCK)
{
pthread_cond_wait(&(p_queue->data_cond), &(p_queue->data_mutex))
}
else
{
printf("[%s]: queue is empty\n", __FUNCTION__)
pthread_mutex_unlock(&(p_queue->data_mutex))
return CNTL_QUEUE_FAIL
}
}
*data = p_queue->data[p_queue->front]
p_queue->front = (p_queue->front + 1)%p_queue->length
pthread_mutex_unlock(&(p_queue->data_mutex))
pthread_cond_signal(&(p_queue->data_cond))
return CNTL_QUEUE_SUCCESS
}
cntl_queue_ret destroy_simple_queue(simple_queue* p_queue)
{
cntl_queue_ret ret = CNTL_QUEUE_SUCCESS
if(NULL == p_queue)
{
printf("[%s] param is error\n", __FUNCTION__)
ret = CNTL_QUEUE_PARAM_ERROR
}
else
{
pthread_mutex_destroy(&(p_queue->data_mutex))
pthread_cond_destroy(&(p_queue->data_cond))
while (p_queue->front != p_queue->rear)//删除队列中残留的消息
{
free(p_queue->data[p_queue->front])
p_queue->front = (p_queue->front + 1)%p_queue->length
}
free(p_queue)
p_queue = NULL
}
return ret
}
void* send_msg_thread(void* arg)
{
queue_buf* send_buf = NULL
int i
send_buf = (queue_buf*)malloc(sizeof(queue_buf))
send_buf->msg_type = 1
strcpy(send_buf->msg_buf, "hello, world!")
printf("first1: rear =%d font =%d\n", ((simple_queue*)arg)->rear, ((simple_queue*)arg)->front)
if (push_simple_queue((simple_queue*)arg, (void*)send_buf, IPC_BLOCK) <0)
{
printf("[%s]: push_simple_queue\n", __FUNCTION__)
return NULL
}
printf("first2: rear =%d font =%d\n", ((simple_queue*)arg)->rear, ((simple_queue*)arg)->front)
queue_buf* send_buf1 = NULL
send_buf1 = (queue_buf*)malloc(sizeof(queue_buf))
send_buf1->msg_type = 2
strcpy(send_buf1->msg_buf, "byebye")
printf("first1: rear =%d font =%d\n", ((simple_queue*)arg)->rear, ((simple_queue*)arg)->front)
if (push_simple_queue((simple_queue*)arg, (void*)send_buf1, IPC_NOWAIT) <0)
{
printf("[%s]: push_simple_queue\n", __FUNCTION__)
return NULL
}
printf("first2: rear =%d font =%d\n", ((simple_queue*)arg)->rear, ((simple_queue*)arg)->front)
return NULL
}
void* recv_msg_thread(void* arg)
{
int i
queue_buf* recv_buf = (queue_buf*)malloc(sizeof(queue_buf))
printf("second1 rear =%d font =%d\n", ((simple_queue*)arg)->rear, ((simple_queue*)arg)->front)
if (CNTL_QUEUE_SUCCESS != pop_simple_queue((simple_queue*)arg, (void**)&recv_buf, IPC_BLOCK))
{
printf("[%s]: pop_simple_queue failed!\n", __FUNCTION__)
return NULL
}
for(i=0i<50i++)
printf("%c", recv_buf->msg_buf[i])
printf("\r\n")
printf("second2: rear =%d font =%d\n", ((simple_queue*)arg)->rear, ((simple_queue*)arg)->front)
printf("second1: rear =%d font =%d\n", ((simple_queue*)arg)->rear, ((simple_queue*)arg)->front)
if (CNTL_QUEUE_SUCCESS != pop_simple_queue((simple_queue*)arg, (void**)&recv_buf, IPC_NOWAIT))
{
printf("[%s]: pop_simple_queue failed!\n", __FUNCTION__)
return NULL
}
for(i=0i<50i++)
printf("%c", recv_buf->msg_buf[i])
printf("\r\n")
printf("second2: rear =%d font =%d\n", ((simple_queue*)arg)->rear, ((simple_queue*)arg)->front)
free(recv_buf)
recv_buf = NULL
return NULL
}
int main(int argc, char* argv[])
{
int ret = 0
pthread_t send_thread_id = 0
pthread_t recv_thread_id = 0
simple_queue* msg_queue = NULL
msg_queue = create_simple_queue(MQ_NAME, MQ_LENGTH_MAX, QUEUE_NO_BLOCK)
if (NULL == msg_queue)
{
printf("[%s]: create simple queue failed!\n", __FUNCTION__)
return -1
}
ret = pthread_create(&send_thread_id, NULL, send_msg_thread, (void*)msg_queue)
if (0 != ret)
{
printf("[%s]: create send thread failed!\n", __FUNCTION__)
return -1
}
ret = pthread_create(&recv_thread_id, NULL, recv_msg_thread, (void*)msg_queue)
if (0 != ret)
{
printf("[%s]: create recv thread failed!\n", __FUNCTION__)
return -1
}
printf("begin join\n")
pthread_join(send_thread_id, NULL)
pthread_join(recv_thread_id, NULL)
printf("end join\n")
ret = destroy_simple_queue(msg_queue)
if (CNTL_QUEUE_SUCCESS != ret)
{
printf("[%s]: destroy simple queue failed!\n", __FUNCTION__)
return -1
}
return 0
}
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)