Module modRecent Private dictRecent As New Dictionary(Of String, String) Private Const RESULT_SPLITTER As String = Chr(0) ' Separates different result combinations in the my.settings string Private Const KEYVAL_SPLITTER As String = Chr(1) ' Separates key = value combinations in individual results strings Public Sub loadRecentResults() ' Purpose: ' Go to application settings, and load what's stored there into our recent results dictionary Dim strRecentResults As String = My.Settings.strRecentResults Dim strResultArr() As String Dim strKeyVal() As String ' If nothing stored or invalid splitter, skip entire process If InStr(strRecentResults, RESULT_SPLITTER) = 0 Then Exit Sub strResultArr = strRecentResults.Split(RESULT_SPLITTER) For intCounter As Integer = 0 To strResultArr.GetUpperBound(0) If InStr(strResultArr(intCounter), KEYVAL_SPLITTER) > 0 Then strKeyVal = strResultArr(intCounter).Split(KEYVAL_SPLITTER) ' Got key/value combination, add to dictionary addMatch(strKeyVal(0), strKeyVal(1)) Else ' Not valid result, ignore End If Next End Sub Public Sub prepareToSaveRecent() ' Preconditions: ' Called from event handler used for handling "before save" event of my.settings ' Purpose: ' Update the settings as appropriate, converting dictionary to a single string Dim strSetting As String = vbNullString ' If nothing to save, then do nothing If dictRecent.Count = 0 Then Exit Sub For Each Key As String In dictRecent.Keys strSetting = strSetting & Key & KEYVAL_SPLITTER & dictRecent(Key) & RESULT_SPLITTER Next ' Remove final result splitter strSetting = strSetting.TrimEnd(RESULT_SPLITTER) My.Settings.strRecentResults = strSetting End Sub Public Sub addMatch(ByVal strSearch As String, ByVal strResult As String) ' Preconditions: ' strSearch = Character user entered ' strResult = Character user clicked after searching for strSearch ' Purpose: ' Add that the user clicked this result to our running storage of ' preferred results If dictRecent.ContainsKey(strSearch) Then ' There are recent results for this search string already ' Take new result remove it if it exists from the list and push it to the front dictRecent(strSearch) = strResult & dictRecent(strSearch).Replace(strResult, vbNullString) Else ' Nothing in the dictionary containing results for this search, create new entry dictRecent.Add(strSearch, strResult) End If End Sub Public Function getMatches(ByVal strSearch As String) As String ' Purpose: ' Returns matches given a search string if any exists ' Postconditions: ' Returns Null String if no results in existance yet ' Returns matches if results exist If dictRecent.ContainsKey(strSearch) Then Return dictRecent(strSearch) Else Return vbNullString End If End Function Public Function getFinalResultsList(ByVal strSearch As String, ByVal strRawResults As String) As String ' Purpose: ' Given a search string and raw results, give the results by adjusting ' the result order so recent items are at front of string, less recent items at rear Dim strMatches As String strMatches = getMatches(strSearch) ' Grab results of previously used characters If strMatches = vbNullString Then ' If nothing to change, just return what we received Return strRawResults Else ' Convert the raw match string to an array of strings each containing 1 character Dim intUBound As Integer = strMatches.Length - 1 Dim strMatchArray(intUBound) As String For intCounter As Integer = 0 To intUBound strMatchArray(intCounter) = strMatches.Substring(intCounter, 1) If InStr(strRawResults, strMatchArray(intCounter)) = 0 Then ' Wait, what was found is not part of the result set ' Security: File-tampering suspected! removeMatch(strSearch, strMatchArray(intCounter)) ' Re-try processing from scratch again Return getFinalResultsList(strSearch, strRawResults) Exit Function End If Next ' Okay, everything is clean now... Now alter results Dim strNewResults As String = strRawResults ' Process array in reverse order so most recent (at top of array) will be first For intCounter As Integer = intUBound To 0 Step -1 ' Remove from rest of results and push to top strNewResults = strMatchArray(intCounter) & strNewResults.Replace(strMatchArray(intCounter), vbNullString) Next ' Return the new results Return strNewResults End If End Function Private Sub removeMatch(ByVal strSearch As String, ByVal strToRemove As String) ' Purpose: ' Removes any match that is determined by another function to be invalid (or result of file corruption/tampering) dictRecent(strSearch) = dictRecent(strSearch).Replace(strToRemove, vbNullString) ' If nothing left in results string, remove from dictionary If dictRecent(strSearch) = vbNullString Then dictRecent.Remove(strSearch) End If End Sub End Module