c - 为什么我的双链表插入失败?

标签 c linked-list

我正在编写一个带有双链表的简单计时器。如果我如下定义链表头,它将起作用。

struct timer_head
{
    struct timer* prev;
    struct timer* next;
    pthread_spinlock_t lock;
};

但是如果我如下定义head,那么插入就会失败,每次插入后我都会丢失之前的节点。

struct timer_head
{
    struct timer* next;
    struct timer* prev;

    pthread_spinlock_t lock;
};

我的部分代码:

struct timer
{
    struct timer* prev;
    struct timer* next;
    struct timespec start;
    struct timespec interval;
    void* par, *par2; 
    /*if handle return 0    */
    /*then delete this timer    */
    /*else restart it       */
    int (*handler) (void* par);
};

struct timer_head
{
    struct timer* prev;
    struct timer* next;
/*
*if i changed the previous definition to 
*code below, then my list insertion will failed
*why?
*/
/*  struct timer* next;
    struct timer* prev;
*/
    pthread_spinlock_t lock;
};
void timer_queue_init(struct timer_head* lst)
{
    pthread_spin_init(&lst->lock, PTHREAD_PROCESS_SHARED);
    lst->next = lst->prev = (struct timer*)lst;
}

static void print_queue(struct timer_head* lst)
{
    pthread_spin_lock(&(lst->lock));
    struct timer* fst = lst->next;

    printf("list travserse:\t");
    while (fst != (struct timer*) lst)
    {
    printf("inteval : %ld, ", fst->interval.tv_nsec);
    fst = fst->next;
    }
    printf("\n");
    pthread_spin_unlock(&(lst->lock));
}


void timer_queue_insert(struct timer_head* lst, struct timer* nt)
{
    pthread_spin_lock(&(lst->lock));
    struct timer* ptr = lst->next;

    /*insert into list, sorted as earlist execute time  */
    while (ptr != (struct timer*) lst &&
        timespec_cmp(&(ptr->start), &(ptr->interval),
        &(nt->start), &(nt->interval)) <= 0)
    {
    printf("next\n");
    ptr = ptr->next;
    }
    nt->next = ptr;
    nt->prev = ptr->prev;

    nt->prev->next = nt;
    ptr->prev = nt;



    /* send signal to manage thread */
    if (!qlen)
    {
    printf("start :%ld s, %ld ns ", nt->start.tv_sec, nt->start.tv_nsec);
    printf("interval :%lds, %ld ns\n", nt->interval.tv_sec, nt->interval.tv_nsec);
    pthread_cond_signal(&wait);
    }
    ++qlen;
    pthread_spin_unlock(&(lst->lock));

    printf("traver after insert\t");
    print_queue(lst);
}

最佳答案

此代码将指向 struct timer_head 的指针转换为指向 struct timer 的指针。

void timer_queue_init(struct timer_head* lst)
{
   pthread_spin_init(&lst->lock, PTHREAD_PROCESS_SHARED);
   lst->next = lst->prev = (struct timer*)lst; /* HERE */
}

只要它们具有相同的结构,这就可以(运气好)。您的 struct timer 如下所示:

struct timer
{
  struct timer* prev;
  struct timer* next;
  ...

因此将 prev 放在 next 之前允许强制转换“碰巧”保留 prevnext 的值>,虽然你绝对不应该这样做。 “碰巧”工作的代码的问题是有时它会碰巧不工作。

关于c - 为什么我的双链表插入失败?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15803703/

相关文章:

java - 链表addLast方法

c - MSYS : Error c compiler cannot create executables

java - 反向链表并写入文件: Java

c - Valgrind 链表内存泄漏

c - 如何从 makefile 运行系统调用并将答案保存在变量中

java - 在不使用内置方法/导入 util 的情况下在 java 中创建链表

java - java中如何删除单向链表中的重复元素?

ios - 获取创建套接字的进程的 pid

C代码多线程Pthread

CUDA __constant__ 对全局内存的尊重。哪个缓存?