需要实现一个消息队列,队列具有 FIFO 特点,即先入先出,在这里采用单向链表实现队列逻辑。

本次要实现的队列要求:

1. 节点可以存放任意类型数据

2. 线程安全

简单说明一下:

1. 创建CFNode类,用作节点,其data属性和next属性都是 atomic,即只能单线程访问属性。

2. 创建CFList类,用以push节点和pop节点

3. 删除操作为不必要操作,在这里实现了纯属个人技痒,同理可实现节点更新、插入等操作,在这里不做过多介绍。

CFList.h文件

 //
// CFList.h
// ListTest
//
// Created by MiaoCF on 2018/2/26.
// Copyright © 2018年 MiaoCF. All rights reserved.
// #import <Foundation/Foundation.h> typedef BOOL(^CFComparator)(id obj1, id obj2); @interface CFNode : NSObject @property (atomic, strong) id data;
@property (atomic, strong) CFNode *next;
@end @interface CFList : NSObject @property (atomic, strong, readonly) CFNode *head;
@property (atomic, strong, readonly) CFNode *tail;
@property (atomic, assign, readonly) NSInteger size; // 1 creat
- (instancetype)initList; // 2 appendNode
- (void)appendData:(id)data; // 3 popNode
- (id)popNode; // 4 deleteNode
- (BOOL)deletNode:(CFNode *)node with:(CFComparator)comparator;// func equal to find node
@end

CFList.m文件

注意:

1. 使用了线程阻塞的互斥锁

2. 删除节点时,用户自己实现 CFComparator 进行比较。

3. 节点重复问题: 有多个节点数据相同 全部删除

 //
// CFList.m
// ListTest
//
// Created by MiaoCF on 2018/2/26.
// Copyright © 2018年 MiaoCF. All rights reserved.
// #import "CFList.h" @implementation CFNode
@end @interface CFList()
@property (atomic, strong) NSLock *mutex;
@end @implementation CFList - (instancetype)initList { self = [super init]; _mutex = [[NSLock alloc] init]; self.head = nil;
self.tail = nil; return self;
} // idea: 记录 head 和 tail 节点, head只管删除节点, tail只管添加节点 - (void)appendData:(id)data {
[_mutex lock]; CFNode *node = [[CFNode alloc] init];
node.data = data;
node.next = nil; if (_head == nil) {
_head = node;
} else {
_tail.next = node;
}
_tail = node;
_size ++; [_mutex unlock];
} - (id)popNode {
[_mutex lock]; id res = nil; if (_head != nil) {
res = _head.data; CFNode *temp = _head;
_head = temp.next;
if (_head == nil) {
_tail = nil;
} temp.next = nil;
_size --;
} [_mutex unlock];
return res;
} // 节点重复问题: 有多个节点数据相同 如何处理? - (BOOL)deletNode:(CFNode *)node with:(CFComparator)comparator{ [_mutex lock]; //空链表
if (_head == nil) {
[_mutex unlock];
return NO;
} CFNode *currentNode = _head;
CFNode *previousNode = currentNode; //从第二个节点开始判断
while (currentNode) { if (comparator(currentNode, node)) { //移除节点 previousNode.next = currentNode.next;
currentNode.next = nil; // 节点重复问题: 有多个节点数据相同 全部删除
if (previousNode.next == nil) { // 一直遍历到末尾,可以清除重复节点 [_mutex unlock];
return YES;
}
}
previousNode = currentNode;
currentNode = currentNode.next; } [_mutex unlock];
return NO;
}
113 @end

OC实现 单向链表的更多相关文章

  1. 复习下C 链表操作(单向链表)

    Object-C 作为C 的包装语言(运行时.消息机制).如果不熟悉C 的话实在玩得太肤浅. 随便深入oc 内部都会接触到C. runtime .GCD.Block.消息机制... 所有强大的功能无不 ...

  2. Reverse Linked List II 单向链表逆序(部分逆序)

    0 问题描述 原题点击这里. 将单向链表第m个位置到第n个位置倒序连接.例如, 原链表:1->2->3->4->5, m=2, n =4 新链表:1->4->3-& ...

  3. 【编程题目】输入一个单向链表,输出该链表中倒数第 k 个结点

    第 13 题(链表):题目:输入一个单向链表,输出该链表中倒数第 k 个结点.链表的倒数第 0 个结点为链表的尾指针.链表结点定义如下: struct ListNode {int m_nKey;Lis ...

  4. 输出单向链表中倒数第k个结点

    描述 输入一个单向链表,输出该链表中倒数第k个结点,链表的倒数第0个结点为链表的尾指针. 链表结点定义如下: struct ListNode { int       m_nKey; ListNode* ...

  5. Linus:利用二级指针删除单向链表

    Linus大神在slashdot上回答一些编程爱好者的提问,其中一个人问他什么样的代码是他所喜好的,大婶表述了自己一些观点之后,举了一个指针的例子,解释了什么才是core low-level codi ...

  6. 【转】Linus:利用二级指针删除单向链表

    原文作者:陈皓 原文链接:http://coolshell.cn/articles/8990.html 感谢网友full_of_bull投递此文(注:此文最初发表在这个这里,我对原文后半段修改了许多, ...

  7. C语言实现单向链表及其各种排序(含快排,选择,插入,冒泡)

    #include<stdio.h> #include<malloc.h> #define LEN sizeof(struct Student) struct Student / ...

  8. 数据结构——Java实现单向链表

    结点类: /** * @author zhengbinMac * 一个OnelinkNode类的对象只表示链表中的一个结点,通过成员变量next的自引用方式实现线性表中各数据元素的逻辑关系. */ p ...

  9. 输入一个单向链表,输出该链表中倒数第K个结点

    输入一个单向链表,输出该链表中倒数第K个结点,具体实现如下: #include <iostream> using namespace std; struct LinkNode { publ ...

随机推荐

  1. JS之setTimeOut与clearTimeOut

    小练习1:针对HTML,分别使用 setTimeout 和 setInterval 实现以下功能: 点击按钮时,开始改变 fade-obj 的透明度,开始一个淡出(逐渐消失)动画,直到透明度为0 在动 ...

  2. JS十进制转二进制(控制位数)

    主要需求:十进制转二进制,可以控制指定的位数. 转化显示后的二进制数为bin-bit中输入的数字宽度.dec-number为5,bin-bit为5,则转化后数字为00101.如果bin-bit小于转化 ...

  3. Python入门-内置函数一

    什么是内置函数?就是python给你提供的拿来直接用的函数,比如print,input等等,截止到python版本3.6.2 python一共提供了68个内置函数,他们就是python直接提供给我们的 ...

  4. react+antd 选项卡切换

    index.js: import React from 'react'; import ReactDOM from 'react-dom'; import CardSecond from './Car ...

  5. php扩展库

    php调用C/C++动态链接库 字数997 阅读28 评论0 喜欢0 本人最近在找实习,移动开发方向.有意者可直接与本人联系.谢谢! 一.简介 一般而言,php速度已经比较快,但是,对于一些较高级开发 ...

  6. vim的日常使用

    Esc 退出编辑模式,输入一下命令 :wq保存后退出 :wq!强制保存后退出 :w保存但不退出 :w!若文件为只读,强制保存 :q不保存退出 :q!不保存强制退出 :e!将文档还原到最原始状态

  7. 24_BlockingQueue接口

    [BlockingQueue常见] [ ArrayBlockingQueue ] 基于数组的阻塞队列的实现,在ArrayBlockingQueue内部,维护了一个定长数组,以便缓存队列中的数据对象,其 ...

  8. 【Android】Android studio 编译问题:finished with non-zero exit value 2

    1.Android studio 编译问题:finished with non-zero exit value 2 问题: Error:Execution failed for task ':andr ...

  9. qt MessageBOX 消息

    void MessageBox::slotQuestion() { switch(QMessageBox::question(this,"Question",tr("It ...

  10. Spring返回json数据

    第一种形式:使用注解@ResponseBody @RequestMapping(value = "/admin/jq", method = RequestMethod.GET) @ ...