private void button2_Click(object sender, EventArgs e) { if (RecordStream != null) { RecordStream.StopRecording(); Stopwatch.Stop(); if (RecordMemoryStream.Length > 0) { RecordMemoryStream.Seek(0, SeekOrigin.Begin); var stream = new RawSourceWaveStream(RecordMemoryStream, RecordStream.WaveFormat); // find the song textBox1.Text = $"Fingerprinting {RecordMemoryStream.Length} bytes, format: {RecordStream.WaveFormat.ToString()}... \r\n"; Application.DoEvents(); //var returnList = GetFingerprint(RecordMemoryStream, RecordStream.WaveFormat.BitsPerSample); List <long> returnList; using (var tempStream = new MemoryStream()) { var buffer = new byte[65536]; var shortBuffer = new short[32768]; var length = 0; while ((length = stream.Read(buffer, 0, buffer.Length)) > 0) { Buffer.BlockCopy(buffer, 0, shortBuffer, 0, length); for (int i = 0; i < length / 2; i += 2) { double outSample = shortBuffer[i] * 0.5 + shortBuffer[i + 1] * 0.5; outSample = Math.Max(outSample, float.MinValue); outSample = Math.Min(outSample, float.MaxValue); tempStream.Write(BitConverter.GetBytes((float)outSample), 0, sizeof(float)); //writer.Write((float)outSample); //System.Diagnostics.Debug.WriteLine(outSample); } } returnList = GetFingerprint(tempStream); } textBox1.Text += "Searching... \r\n"; Application.DoEvents(); var foundList = new List <KeyValuePair <SongData, int> >(); var noMatches = new List <KeyValuePair <SongData, int> >(); var tempList = new List <SongTimeData>(); foundList.Clear(); tempList.Clear(); int fingerprintPos = 0; foreach (var fingerprint in returnList) { IEnumerable <SongTimeData> matchList; if (songDb.TryGetValue(fingerprint, out matchList)) { tempList.AddRange(matchList.Select(x => { x.Position -= fingerprintPos; return(x); })); } fingerprintPos++; } textBox1.Text += $"Found {tempList.Count} matches...\r\n"; Application.DoEvents(); foreach (var item in tempList) { if (!foundList.Where(x => x.Key.FileName == item.SongData.FileName).Any()) { var foundItem = tempList.Where(x => (x.SongData.FileName == item.SongData.FileName)).ToArray(); if (foundItem != null && foundItem.Any()) { var minIndex = foundItem.Min(x => x.Position); int score = 0; int matches = foundItem.Length; for (int i = 0; i < foundItem.Length; i++) { score += Math.Abs(foundItem[i].Position - minIndex); } foundList.Add(new KeyValuePair <SongData, int>(item.SongData, score / matches)); noMatches.Add(new KeyValuePair <SongData, int>(item.SongData, matches)); } } } SongData bestMatch = null; int minScore = int.MaxValue; int maxMatches = 0; int count = 0; foreach (var item in noMatches.OrderByDescending(x => x.Value)) { var score = foundList.Where(x => (item.Key.FileName == x.Key.FileName)).FirstOrDefault(); if ((item.Value >= 2)) { if (count < 20) { textBox1.Text += $"{count}: Match {item.Key.TrackName} {item.Value} times - Score: {score.Value}\r\n"; } count++; if (item.Value > maxMatches || ((item.Value == maxMatches) && score.Value < minScore)) { bestMatch = item.Key; minScore = score.Value; maxMatches = item.Value; } } } if (bestMatch != null) { textBox1.Text += $"\r\nBest match: {bestMatch.TrackName}"; } } } }