2013级测试赛 - F 播放器

原创 2013年12月04日 11:24:41

Description

shadow喜欢听音乐,于是v11自己写了个播放器送给了shadow,这个播放器有一个播放列表,一个“下一首”按钮,一个“上一首”按钮,还有一个播放记录。

一开始播放器会播放播放列表中的第一首歌,当按下“下一首”按钮时,它会播放当前歌曲在播放列表中的下一首歌,若当前歌曲就是播放列表中的最后一首歌时,它仍会播放播放列表中的最后一首歌;当按下“上一首”按钮时,它会清除播放记录中的最后一首歌,并播放清除后播放记录中的最后一首歌,若清除后播放记录为空,则播放播放列表中的第一首歌;当按下播放列表中的某一首歌曲,它会播放该首歌曲。

任何时候,当播放器播放一首歌时,如果该歌曲与播放记录中的最后一首不同或者播放记录为空,便将该歌曲添加到播放记录中成为最后一首。

现在shadow对播放器进行了一系列操作,那么你能告诉我shadow进行每一个操作后,播放器在播放哪首歌吗?

Input

输入数据第一行包含一个整数T,表示测试数据的组数。对于每组测试数据:

第一行包含两个整数n( 0 < n <= 500 )、m( 0 < m <= 10000),分别表示播放列表中有n首歌曲,shadow进行了m项操作,播放列表中歌的编号依次为1,2,3……n 。

接下来m行,每行为以下三种形式之一:

PRE 表示按下了“上一首”按钮。

PLAY x 其中x为一个整数( 0 < x <= n ),表示按下了播放列表中的第x首歌。

NEXT 表示按下了“下一首”按钮。

Output

对于每组数据:输出m行,每行一个整数,表示执行了一项操作后播放器正在播放的歌曲。

Sample Input

1
5 10
PRE
NEXT
PLAY 5
NEXT
PLAY 5
PLAY 3
NEXT
PRE
PRE
PRE

Sample Output

1
2
5
5
5
3
4
3
5
2

Hint

 

  这个题也算我对链表的第一次应用,首先摆出开始回馈编译错误的代码

#include <stdio.h>
#include <stdlib.h>

typedef struct
{
    int play;
    struct lis *next;
    struct lis *last;
} lis;

int main()
{
    int ii = 0,nn = 0;
    int n = 0,m = 0;
    int len = 0,mp3 = 0,quan = 0;
    char c[10],*p;
    lis *head = NULL;
    lis *ne,*t;  //NEW


    freopen ("1.txt","r",stdin);

    scanf ("%d",&nn);
    for (ii = 0; ii < nn; ii++)
    {
        head = malloc (sizeof (lis) * 1);
        ne = head;
        ne->play = 1;
        ne->next = NULL;
        ne->last = NULL;

        scanf ("%d %d",&n,&m);
        getchar ();
        while(m--)
        {
            gets (c);
            p = c;
            len = 0;
            while (*p != '\0')
            {
                len++;
                p++;
            }

            if(len >= 6)
            {
                p--;
                quan = 1;
                mp3 = 0;
                while (*p != ' ')
                {
                    mp3 += ((int)*p - 48) * quan;
                    quan *= 10;
                    p--;
                }

                if (mp3 != t->play)
                {
                    t = malloc (sizeof (lis) * 1);
                    ne->next = t;
                    t->last = ne;
                    ne = ne->next;
                    ne->play = mp3;
                    ne->next = NULL;
                }
            }
            else if (len == 4)
            {
                if (ne->play < n)
                {
                    t = malloc (sizeof (lis) * 1);
                    t->play = ne->play + 1;
                    ne->next = t;
                    t->last = ne;
                    ne = ne->next;
                    ne->next = NULL;
                }
            }
            else if (len == 3)
            {
                if (ne != head)
                {
                    free (ne);
                    ne = ne->last;
                    ne->next = NULL;
                }
            }
            printf ("%d\n",ne->play);
        }
    }

    return 0;
}


 

回馈是这个样子的

修改之后,我发现问题出在了结构体上,我一般定义结构体为了省事都是typedef struct,这样在main函数中声明变量可以直接写结构体名而不用写struct,但是用C++编译行不通,即使是在CB中,也无法编译成功,可以归结为C和C++的差异,在语法上,还有一个问题属于其差异,就是“t = malloc (sizeof (lis) * 1);”,在C中可以这样写,而在C++中不可以,在《C P P》中讲内存管理的时候虽然只是强调在C中最好加上(lis*)强制转换以加强对C++的可移植性,但对于C++的程序来讲,就一定要加上了,这个还需要养成习惯。

对于上述,我把typedef去掉并把所有lis换为struct lis,加上强制转换类型,终于没有了语法错误,但WA也来了。(从构建链表到WA已经用了一个多小时,事实证明,链表对于我还算很陌生)

 

 

学长修改

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

struct lis
{
    int play;
    struct lis *next;
    struct lis *last;
};

int main()
{
    int ii = 0,nn = 0;
    int n = 0,m = 0;
    int len = 0,mp3 = 0,quan = 0;
    char c[10],*p;
    struct lis *head = NULL;
    struct lis *ne,*t;  //NEW


    //freopen ("1.txt","r",stdin);

    scanf ("%d",&nn);
    for (ii = 0; ii < nn; ii++)
    {
        head = (struct lis *)malloc (sizeof (struct lis) * 1);
        ne = head;
        ne->play = 1;
        ne->next = NULL;
        ne->last = NULL;

        t = NULL;//将t指空

        scanf("%d %d%*c",&n,&m);
        //getchar ();
        while(m--)
        {
            gets (c);
            p = c;
            len = 0;
            //这里可以用 strlen()
            //或者换一个思路 用strcmp()
            //在课本上貌似都有 可以去看一下
            while (*p != '\0')
            {
                len++;
                p++;
            }
            //if(strcmp("PLAY",c) == 0)
            if(len >= 6)
            {
                p--;
                quan = 1;
                mp3 = 0;
                while (*p != ' ')
                {
                    mp3 += ((int)*p - 48) * quan;
                    quan *= 10;
                    p--;
                }
                //scanf("%d",&mp3);
                if (mp3 > n)
                    mp3 = n;

                //printf("mp3 = %d\n",mp3);

                //此处t有可能没有分配内存
                //比如第一组输入即为 PLAY 5
                //if (mp3 != t->play)
                if(mp3 != ne->play)//逻辑或与 的 短路原则
                {
                    t = (struct lis *)malloc (sizeof (struct lis) * 1);
                    ne->next = t;
                    t->last = ne;
                    ne = ne->next;
                    ne->play = mp3;
                    ne->next = NULL;
                }
            }
            else if (len == 4 || c[0] == 'N')
            //else if(strcmp("NEXT",c) == 0)
            {
                if (ne->play < n)
                {
                    t = (struct lis *)malloc (sizeof (struct lis) * 1);
                    t->play = ne->play + 1;
                    ne->next = t;
                    t->last = ne;
                    ne = ne->next;
                    ne->next = NULL;
                }
            }
            else if (len == 3 || c[0] == 'P')
           // else if(strcmp("PRE",c) == 0)
            {
                if (ne != head)
                {
                    t = ne;
                    ne = ne->last;
                    free (t);
                    ne->next = NULL;
                }
            }
            printf ("%d\n",ne->play);
           // printf ("\t%#x\n",&ne);
        }
    }
    return 0;
}


 

反思后修改

#include <stdio.h>
#include <stdlib.h>

struct lis
{
    int play;
    struct lis *next;
    struct lis *last;
};

int main()
{
    int ii = 0,nn = 0;
    int n = 0,m = 0;
    int len = 0,mp3 = 0,quan = 0;
    char c[10],*p;
    struct lis *head = NULL;
    struct lis *ne,*t;  //NEW


    //freopen ("1.txt","r",stdin);

    scanf ("%d",&nn);
    for (ii = 0; ii < nn; ii++)
    {
        head = (struct lis *)malloc (sizeof (struct lis) * 1);
        ne = head;
        ne->play = 1;
        ne->next = NULL;
        ne->last = NULL;
        //第一个错误没有把t初始化
        t = head;

        scanf ("%d %d",&n,&m);
        getchar ();
        while(m--)
        {
            gets (c);
            p = c;
            len = 0;
            while (*p != '\0')
            {
                len++;
                p++;
            }

            if(len >= 6)
            {
                p--;
                quan = 1;
                mp3 = 0;
                while (*p != ' ')
                {
                    mp3 += ((int)*p - 48) * quan;
                    quan *= 10;
                    p--;
                }
                if (mp3 > n)
                    mp3 = n;
                    
                if (mp3 != ne->play)
                {
                    t = (struct lis *)malloc (sizeof (struct lis) * 1);
                    ne->next = t;
                    t->last = ne;
                    ne = ne->next;
                    ne->play = mp3;
                    ne->next = NULL;
                }
            }
            else if (len == 4)
            {
                if (ne->play < n)
                {
                    t = (struct lis *)malloc (sizeof (struct lis) * 1);
                    t->play = ne->play + 1;
                    ne->next = t;
                    t->last = ne;
                    ne = ne->next;
                    ne->next = NULL;
                }
            }
            else if (len == 3)
            {
                if (ne != head)
                {
                    t = ne;
                    ne = ne->last;
                    free (t);
                    ne->next = NULL;
                }
            }
            printf ("%d\n",ne->play);
        }
    }

    return 0;
}


其实我WA的本质就是没有清楚上一个链节与当前链节的关系,主要表现就是在PLAY X中判断是否重复出现了问题。

通过这个题,明显感觉到当大量指针涌来时,让我十分混沌,但是链表就是由指针串起来的,链表的操作基本都是指针完成的,指针指向那里?其空间代表的意义是什么?对其操作的目的以及最终会达到什么效果,一定要明了。比如此题中ne指向是当前链节,t可能是上一个链节(t需要初始化以免在就一个链节的情况下指向不明了),也可能是当前链节(初始化后指向第一个链节)。

不仅仅是链表什么的,在判断以及strcmp的使用上还不够熟悉,需要专门学习。

相关文章推荐

【51单片机学习笔记】基于STC11F04E的蜂鸣器音乐播放器

基于STC11F04E控制蜂鸣器制作的小型音乐播放器

嵌入式39.300.300F.800系列-MP4播放器

  • 2013年12月11日 09:55
  • 1.95MB
  • 下载

基于STC11F04E的蜂鸣器音乐播放器

  • 2017年06月25日 02:18
  • 44.43MB
  • 下载

微信小程序开发之音乐播放器 真机测试 audio API

简单的试了试播放器,还是有不少坑的.开始在模拟器上跑,一直没有声音,总是刚开始播放就暂停.做个笔记. 准备资源: 音乐图片地址:http://ac-5g9r20ds.clouddn.com/63b...

STM32F1 做的MP3播放器

  • 2017年06月09日 08:10
  • 8.76MB
  • 下载

s w f播放器

  • 2013年10月07日 16:24
  • 1.84MB
  • 下载

Redrain仿酷狗音乐播放器开发完毕,发布测试程序

转载请说明原出处,谢谢~~        从暑假到现在中秋刚过,我用duilib开发仿酷狗播放器大概经历了50天。做仿酷狗的意图只是看原酷狗的界面比较漂亮,想做个完整一些的工程来练习一下duilib。...

基于msp430f149做的mp3播放器

  • 2010年10月24日 13:05
  • 184KB
  • 下载

Android 播放器外挂字幕支持测试

最近需要在播放器上面添加一个外挂字幕和音轨切换的功能,不知从何下手,下面的几个播放器目前算是做的比较好的,从网络上抓取了一些信息,希望能找到点参考价值 再次申明如下文章来之于网络,非...
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:2013级测试赛 - F 播放器
举报原因:
原因补充:

(最多只允许输入30个字)