Here's what I have for a data recorder. It is NOT tested. I suggest you learn how the ErrorHandler operates first, then go thru the rest of the Modules and add the same process to any Procedures you think might need it. By the time you've done that, you should have a good handle on all the Classes, (User Defined Objects.)
Theory of Operation
All Code uses Worksheet CodeNames
Bet_Angel: Main Driver is Worksheet_Change Event Sub; Starts And Stops code Operation with Macros, "StartRecording" and "StopRecording"; Observes Worksheet Changes and sends appropriate data to the Recorder.
Bet Angel Worksheet Events
Range("A1") Change: Call Recorder.StartUpdate
Range(AF9") Change: Let Recorder.HorsesData = HorsesDataTable.Value
Range("C2") Change: Let Recorder.MarketData = MarketDataRange.Value
Recorder, (clsRecorder): Owned by Bet_Angel; Generates a Unique Key; Sends MicroTime and Key to the MarketWriter, all Horse Data and Key to HorsesWriter, Then all Market Data to MarketWriter.
MicroTimer, (clsMicroTimer): Owned by Recorder; Provides an Elapsed time in Seconds, to microsecond accuracy.
MarketWriter, (clsTableWriter_Market): Owned by Recorder; Parses 2D MarketData into a 1D OutPut array with Key and MicroTime included; Writes Output to MarketData, A Worksheet
HorsesWriter, (clsTableWriter_Brand): Owned by Recorder; Parses a Defacto 3D array of Horses Data into a simple 2D OutPutData array with Key included; Writes Output to BrandData, A Worksheet.
ErrorHandler, [Module- ErrorHandler]: Has one function, Accepts a String, selects the Message Associated with that String, Displays Message, Stops all code execution.
______________________________________________
The Processes above have been organized to use time as efficiently as possible since Updates are coming in at 20 - 50 per second.