歌词解析器代码详情Word文件下载.docx

上传人:b****5 文档编号:21898554 上传时间:2023-02-01 格式:DOCX 页数:18 大小:24.71KB
下载 相关 举报
歌词解析器代码详情Word文件下载.docx_第1页
第1页 / 共18页
歌词解析器代码详情Word文件下载.docx_第2页
第2页 / 共18页
歌词解析器代码详情Word文件下载.docx_第3页
第3页 / 共18页
歌词解析器代码详情Word文件下载.docx_第4页
第4页 / 共18页
歌词解析器代码详情Word文件下载.docx_第5页
第5页 / 共18页
点击查看更多>>
下载资源
资源描述

歌词解析器代码详情Word文件下载.docx

《歌词解析器代码详情Word文件下载.docx》由会员分享,可在线阅读,更多相关《歌词解析器代码详情Word文件下载.docx(18页珍藏版)》请在冰豆网上搜索。

歌词解析器代码详情Word文件下载.docx

//存储歌曲的信息

/*************************************************************************

*函数功能:

歌词解析器整体的控制

*参数:

*返回值:

**************************************************************************/

intmain()

{

intfile_length=0;

//存储lrc文件内容的大小

char*file_buf=NULL;

//指向malloc的空间,其中存放着lrc文件中所有的内容

char*lrc_text[200]={NULL};

//指向,按照\r\n切割后的一行歌词

intlrc_line=0;

//lrc文件中的行数

inti=0;

LRC*head=NULL,*p;

//head记录歌词链表头

ints_time=0;

//模拟时间变量

file_buf=read_src_file(&

file_length,"

./lrc/兰亭序.lrc"

);

//从lrc文件中读出歌词内容

lrc_line=strtok_lrc_buf(lrc_text,file_buf);

//按行切割歌曲内容

lrc_head_resolve(song_msg,lrc_text);

//切割歌曲信息

print_song_message(song_msg);

//显示歌曲信息

head=lrc_resolve(lrc_line,lrc_text);

//保存时间:

歌词到链表中

//print(head);

//遍历链表,用来测试链表

//ShellExecute(NULL,NULL,"

TTPlayer.exe"

"

兰亭序.mp3"

NULL,1);

//开启千千静听

m_time.second=0;

m_time.minute=0;

while

(1)//每秒钟到链表里面去找相应的歌词,如果找到那么就显示

{

/*

*1.定位光标,显示歌词

*/

GoToXY(20,5);

printf("

%02d:

%02d"

m_time.minute,m_time.second);

p=search(head,s_time);

//到连表里查找当前时间点对应的歌词,如果有那么就返回歌词的首地址

if(p!

=NULL)

{

lrc_show(p);

}

*1.运行模拟时间

Sleep(500);

//延时,注意在windows平台Sleep

(1);

延时1毫秒

s_time=s_time+1;

++m_time.second;

if(m_time.second==60)

m_time.second=0;

++m_time.minute;

if(m_time.minute==60)

m_time.minute=0;

}

return0;

}

/*****************************************************************************/

lrc.h

#ifndef__LRC_H__

#define__LRC_H__

typedefstructlrc{

inttime;

charlrc_buf[200];

structlrc*next;

}LRC;

externchar*read_src_file(int*file_length,char*src_file_name);

externintstrtok_lrc_buf(char*lrc_text[],char*file_buf);

externvoidlrc_head_resolve(char*lrc_head_info[],char*lrc_text[]);

externvoidprint_song_message(char*msg_info[]);

externLRC*lrc_resolve(intlrc_line,char*lrc_text[]);

externLRC*InsertList(LRC*head,LRC*lrc_link);

externvoidprint(LRC*head);

externLRC*search(LRC*head,inttime);

externvoidlrc_show(LRC*pi);

externvoidprint_lrc(char*lrc);

#endif

lrc.c

读出文件内容

*file_length:

整型指针,此地址中保存文件字节数。

*src_file_name:

文件名字,从此文件中读取内容。

读出字符串的首地址

char*read_src_file(int*file_length,char*src_file_name)

unsignedlongintFILE_SIZE=0;

char*src_file_text=NULL;

FILE*fp=NULL;

fp=fopen(src_file_name,"

rb"

if(fp==NULL)

open%sfaild\n"

src_file_name);

return0;

fseek(fp,0,SEEK_END);

FILE_SIZE=ftell(fp);

*file_length=FILE_SIZE;

//返回歌词文件内容的大小

rewind(fp);

//一定要把“文件指针”移动到文件开始处

src_file_text=(char*)malloc(FILE_SIZE);

if(fread(src_file_text,FILE_SIZE,1,fp)==0)

readfromsrc_filefaild\n"

returnNULL;

fclose(fp);

//关闭文件

returnsrc_file_text;

/************************************************************************

切割歌词数组

*lrc_text指针数组,让其指针指向切出来的内容

*file_buf歌词内容数组

*返回值:

切割出来的字符串的个数

*************************************************************************/

intstrtok_lrc_buf(char*lrc_text[],char*file_buf)

lrc_text[i++]=strtok(file_buf,"

\r\n"

while((lrc_text[i++]=strtok(NULL,"

))!

=NULL);

returni;

/**************************************************************************

解析lrc前四行,歌曲的信息如歌手、专辑等。

*lrc_text指针数组lrc中的前四行

*song_msg指针数组用来指向处理好的歌曲信息

voidlrc_head_resolve(char*song_msg[],char*lrc_text[])

char*message[]={"

[ti"

[ar"

[al"

[by"

};

char*temp;

for(i=0;

i<

4;

i++)//循环四次找到四个头信息的开始

if(strncmp(lrc_text[i],message[i],3)==0)

temp=lrc_text[i];

/*

[ti:

兰亭序]

[ar:

李维]

[al:

情已逝DSD]

[by:

朱古力]

*/

while(*temp!

='

]'

)//找到头信息],然后改为'

\0'

{

temp++;

}

*temp='

;

song_msg[i]=lrc_text[i]+4;

//跳过ti:

三个字母,保存歌词信息;

打印歌曲信息

*song_msg歌曲信息指针数组指向歌曲头信息内容

*注意点:

voidprint_song_message(char*song_msg[])

char*name[4]={"

歌名:

"

歌手:

专辑:

制作:

i++)

%s%s\n"

name[i],song_msg[i]);

解析歌曲信息

*lrc_text指向歌词内容(以行的方式存储)的指针数组

*lrc_line歌词的行数

LRC*lrc_resolve(intlrc_line,char*lrc_text[])

LRC*head=NULL,*lrc_link;

inti=0,j=0,CurOffset;

char*LrcFile;

intCurTime[10];

//用来暂时记录歌词中的时间,单位为:

毫秒

intnum=0;

//用来暂时记录本句歌词有多少个时间与其对应

for(i=4;

lrc_line-1;

LrcFile=lrc_text[i];

//一行的歌词:

[00:

25.21]兰亭临帖行书如行云流水

CurOffset=1;

//标识时间位置的偏移量

if((LrcFile[CurOffset])>

='

0'

&

&

(LrcFile[CurOffset])<

9'

)//检测到歌词时间标签

char*lrc;

//用来暂时记录时间后面的歌词

num=0;

//解析每句歌词时,要把本句歌词对应的时间数初始化为0

//[00:

//[02:

04.94][00:

36.09]我想大声宣布对你依依不舍

while(LrcFile[CurOffset]>

LrcFile[CurOffset]<

)//取出这句歌词所有时间标签

CurTime[num++]=(((LrcFile[CurOffset]-'

)*10+(LrcFile[CurOffset+1]-'

))*60+((LrcFile[CurOffset+3]-'

)*10+LrcFile[CurOffset+4]-'

))*1000+\

(LrcFile[CurOffset+6]-'

)*100+(LrcFile[CurOffset+7]-'

)*10;

CurOffset=CurOffset+10;

//解析一句歌词在不同时间出现的情况时,需要把指针往后偏移10

//lrc=&

LrcFile[CurOffset-1];

//得到这句歌词首地址“我想大声宣布对你依依不舍”

lrc=LrcFile+10;

//根据本句歌词对应的时间个数,把歌词与时间保存到链表中

for(j=0;

j<

num;

j++)

lrc_link=(LRC*)malloc(sizeof(LRC));

//申请节点,存放解析出歌词与时间

lrc_link->

time=CurTime[j];

strcpy(lrc_link->

lrc_buf,lrc);

//将解析出的时间、歌词内容插入到单向链表并进行排序

head=InsertList(head,lrc_link);

returnhead;

往链表中插入歌词节点。

*head链表的头节点地址。

*lrc_link将要插入的节点首地址。

插入之后链表的头节点的地址

LRC*InsertList(LRC*head,LRC*lrc_link)

LRC*pb,*pf;

if(head==NULL)//如果原先链表为空head为pi

lrc_link->

next=NULL;

head=lrc_link;

returnhead;

pb=pf=head;

while((lrc_link->

time>

pb->

time)&

(pb->

next!

=NULL))//查找比pi->

num更大的节点

{

pf=pb;

pb=pb->

next;

if(lrc_link->

time<

=pb->

time)//如果上面的while循环式因为找到lrc_link->

time而推出的

if(pb==head)//如果找到的节点为第一个,则pi应该放到head的前面

lrc_link->

next=head;

//把pi放到链表里

head=lrc_link;

//把pi变成头节点

else//如果是pb普通节点的话在pf和pb之间插入pi

pf->

next=lrc_link;

//pb的前一个节点的指针域指向pi

next=pb;

//pi的指针域指向pb

else//如果链表中的节点的time都比pi->

time小,则插到链表尾端

pb->

//pb的指针域指向pi

//pi的下一个为NULL即pi为链表的尾

从歌词链表中查找时间为time的结点

*time要查询的时间

时间为time的结点的首地址

LRC*search(LRC*head,inttime)//在一个已建立的链表中查找某一节点

LRC*p,*pi=NULL;

p=head;

//导入已存在链表的头文件

while((p->

time/1000)!

=time&

p->

=NULL)//判断是否找到要找的数据,判断是否到链表尾。

p=p->

//不是要找的结点后移一步

if((p->

time/1000)==time)

pi=p;

//找到数据则返回相应指针地址

elseif(p->

next==NULL)//到链表尾则打印数据未找到

pi=NULL;

returnpi;

遍历链表

voidprint(LRC*head)

printf("

\n链表所有信息如下:

\n"

TIME\t\tLRC_BUF\n"

while(head!

%d\t\t%s\n"

head->

time,head->

lrc_buf);

head=head->

{//表示日期时间的数据结构

externTIMEm_time;

externchar*song_msg[4];

charlrc_buf[6][200]={"

歌词显示

*pi新查找到得结点

voidlrc_show(LRC*pi)

staticintx=0,y=11;

staticintlrc_num=0;

if(lrc_num<

6)

*1:

前6行歌词显示的方式

*2:

strcpy(lrc_buf[lrc_num],pi->

//lrc_num=0、1、2、3、4、5

if(lrc_num>

0)

GoToXY(x,y-1);

printf("

%s\n"

lrc_buf[lrc_num-1]);

//只覆盖上1次显示绿颜色的那一行歌词

GoToXY(x,y);

print_lrc(pi->

//当

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 职业教育 > 中职中专

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1