C # parse the Lrc lyrics file,
Many people have written a large piece of Character Processing code when parsing the lyrics file, but they do not quite understand it. So I have studied it myself. First of all, I want to understand the time format of the Lrc file: 1. Standard Format: [minute: second. millisecond] lyrics Note: (as shown in the figure on the right) brackets, colons, and periods all require the English input status; 2. Other formats ①: [minute: Second] lyrics; 3. Other formats ②: [minute: Second: millisecond] The lyrics. Compared with the standard format, the dot after the second is changed to a colon. Id format: the format is "[Identification name: value]". Case-insensitive. The following are predefined labels. [Ar: artist name] [ti: Qu name] [al: album name] [by: Editor (person who edits LRC lyrics)] [offset: time compensation value] The unit is millisecond. A positive value indicates the overall advance, and a negative value indicates the opposite. This is used to adjust the overall display speed. The standard is good. I will follow the standard.
Public class Lrc {// <summary> /// song // </summary> public string Title {get; set ;} /// <summary> /// Artist /// </summary> public string Artist {get; set ;} /// <summary> /// Album /// </summary> public string Album {get; set ;} /// <summary> /// author of the lyrics /// </summary> public string LrcBy {get; set ;} /// <summary> /// Offset /// </summary> public string Offset {get; set ;}/// <summary> /// lyrics /// </Summary> public Dictionary <double, string> LrcWord = new Dictionary <double, string> (); /// <summary> /// obtain the lyrics /// </summary> /// <param name = "LrcPath"> Lyrics </param> // <returns> return the lyrics (Lrc instance) </returns> public static Lrc InitLrc (string LrcPath) {Lrc lrc = new Lrc (); using (FileStream fs = new FileStream (LrcPath, FileMode. open, FileAccess. read, FileShare. read) {string line; using (StreamReader Sr = new StreamReader (fs, Encoding. Default) {while (line = sr. ReadLine ())! = Null) {if (line. startsWith ("[ti:") {lrc. title = SplitInfo (line);} else if (line. startsWith ("[ar:") {lrc. artist = SplitInfo (line);} else if (line. startsWith ("[al:") {lrc. album = SplitInfo (line);} else if (line. startsWith ("[by:") {lrc. lrcBy = SplitInfo (line);} else if (line. startsWith ("[offset:") {lrc. offset = SplitInfo (line);} else {Regex regex = new Regex (@ "\ [([0-9. :] *) \] + (. *) ", RegexOptions. compiled); MatchCollection mc = regex. matches (line); double time = TimeSpan. parse ("00:" + mc [0]. groups [1]. value ). totalSeconds; string word = mc [0]. groups [2]. value; lrc. lrcWord. add (time, word) ;}}}return lrc ;}/// <summary >/// Process Information (Private method) /// </summary> /// <param name = "line"> </param> /// <returns> returns the basic information </returns> static string SplitInfo (string line) {return line. substring (line. indexOf (":") + 1 ). trimEnd (']');}
Code line: Lrc lrc = Lrc. InitLrc ("test. lrc ");
I put the separated lyrics in Dictionary <double, string>. Of course, you can use arrays to store them directly. The format depends on the actual usage. I will give them to TimeSpan.
Test:
C language ^ how to use
A1 = 0x01; // 0000 0001
A2 = 0x00; // 0000 0000
A3 = 0x03; // 0000 0011
A4 = 0x02; // 0000 0010
B1 = a1 ^ a2; // 0000 0001
B2 = a1 ^ a3; // 0000 0010
B3 = a1 ^ a4; // 0000 0011
^ XOR operator. The bitwise value is 0 and the difference is 1. See the example above.
//
Examples of simple and practical problems:
====================================
======= A ======= B =========
There are two circuits on the top. The two switches are a and B respectively. The opening status is \ [1], and the closing status is/[0].
If both circuits are enabled or disabled.
If a turns on [1], B turns off [0], and circuit 1 Powers on
=====================
If a disables [0], B enables [1], and circuit 2 powers on.
====================================
In summary, the circuit fails in the and B states simultaneously [0]. When a and B are different, the power is charged [1].
C language ^ how to use
A1 = 0x01; // 0000 0001
A2 = 0x00; // 0000 0000
A3 = 0x03; // 0000 0011
A4 = 0x02; // 0000 0010
B1 = a1 ^ a2; // 0000 0001
B2 = a1 ^ a3; // 0000 0010
B3 = a1 ^ a4; // 0000 0011
^ XOR operator. The bitwise value is 0 and the difference is 1. See the example above.
//
Examples of simple and practical problems:
====================================
======= A ======= B =========
There are two circuits on the top. The two switches are a and B respectively. The opening status is \ [1], and the closing status is/[0].
If both circuits are enabled or disabled.
If a turns on [1], B turns off [0], and circuit 1 Powers on
=====================
If a disables [0], B enables [1], and circuit 2 powers on.
====================================
In summary, the circuit fails in the and B states simultaneously [0]. When a and B are different, the power is charged [1].