现在的位置: 首页 > 综合 > 正文

链表应用之—–整理音乐

2012年11月03日 ⁄ 综合 ⁄ 共 2093字 ⁄ 字号 评论关闭

整理音乐


Time Limit: 1000MS Memory limit: 65536K

题目描述

请用链表完成下面题目要求。
xiaobai 很喜欢音乐,几年来一直在收集好听的专辑。他有个习惯,每次在听完一首音乐后会给这首音乐打分,而且会隔一段时间给打好分的音乐排一个名次。今天 xiaobai打开自己的音乐文件夹,发现有很多不同时期打过分的排好序的子音乐文件夹,他想把这些音乐放到一块,组成一个分数有序的序列。由于音乐文件很多,而文件里音乐的数目也是不确定的,怎么帮帮 xiaobai完成这件工作呢?
   

输入

输入数据第一行为一个整数nn<1000),代表文件夹的数量。接下来是n个文件夹的信息,每个文件夹信息的第一行是一个数字m,代表这个文件夹里有m首歌,后面m行每行一个歌曲名、分数,之间用空格分开。

输出

输出一行,为所有音乐组成的一个序列,音乐只输出名字。

如果音乐分数相同则按照音乐名字典序进行排序。

示例输入

3
4
aaa 60
aab 50
aac 40
aad 30
2
kkk 60
kkd 59
3
qow 70
qwe 60
qqw 20

示例输出

qow aaa kkk qwe kkd aab aac aad qqw
 
 
 分析:本题考验的是对链表的建立输出,最重要是对有序链表的合并等知识的掌握。纯属基础性问题,掌握链表的基本知识即可做出本题。
#include <stdio.h>
#include <malloc.h>
#include <string.h>

struct node  //建立结点
{
    char name[10];   //歌曲的名字变量
    int s;           //歌曲的分数
    struct node *next;    //指针域
};

//--------建立链表-------
struct node *create1(int num)
{
    struct node *head,*tail,*p;
    int i;
    head = (struct node*)malloc(sizeof(struct node));   //建立头结点
    head->next = NULL;       
    tail = head;      //尾指针指向头结点
    for(i = 1;i <= num;i++)
    {
        p = (struct node*)malloc(sizeof(struct node));
        p->next = NULL;
        scanf("%s %d",p->name,&p->s);
        tail->next = p;   //形成链表间的结点连接
        tail = p;         //尾结点指向下一个结点
    }
    return (head);        //返回头结点

}
//--------链表合并--------
/*归并过程是一个新建链表的过程,先借用原来链表头结点生成一个空的新链表,
 同时两个旧链表指针指向要比较的结点的位置,用p1, p2指向两个链表的当前结点。
struct node *merg(struct node *head1,struct node *head2)
{
    struct node *tail,*p1,*p2;
    p1 = head1->next;   //将head1链表复制给p1
    p2 = head2->next;   //将head2链表复制给p2

    tail = head1;    //尾结点指向head1
    free(head2);   //释放head2
    while(p1&&p2)
    {
        if(p1->s >= p2->s)  //归并的条件
        {
            if(strcmp(p1->name,p2->name) < 0)   //按照音乐名字典序进行排序
             {   tail->next  = p1;    //把数值较大的结点从所在链表删除并插入到新链表尾结点之后,同时使得新链表的尾指针指向新的尾结点
                 tail = p1;           //被删结点的旧链表游动指针往后移动,指向后面的结点。
                 p1 = p1->next;
             }
             else
                {
                    tail->next = p2;
                    tail = p2;
                    p2 = p2->next;
                }
        }else
        {
            tail->next = p2;
            tail = p2;
            p2 = p2->next;
        }

    }
    if(p1)   //p1的结点还剩余,则尾指针指到p1
        tail->next = p1;
    else
        tail->next = p2;

    return (head1);
}
 //-------输出链表--------
 void output(struct node *head)
 {

     struct node *p;
     p = head->next;
     while(p->next != NULL)
     {
         printf("%s ",p->name);
         p = p->next;

    }
    printf("%s\n",p->name);
    free(p);
 }
int main()
{
    struct node *Head1,*Head2;
    int NUM,j,Num;
    scanf("%d",&NUM);
    scanf("%d",&Num);
    Head1 = create1(Num);  //首先建立指针1,判断是否输入的组数大于1,如果等于1,则输出链表1,
                           //否则,继续输入链表2,与链表1合并。
    if(NUM == 1)
    {
        output(Head1);

    }else
    {
          for(j = 2;j <= NUM;j++)
       {
           scanf("%d",&Num);
           Head2 = create1(Num);
           Head1 = merg(Head1,Head2);
       }
    }
      output(Head1);
      free(Head1);
    return 0;
}

 

抱歉!评论已关闭.