Jean_D 1 Posted Wednesday at 08:00 PM (edited) Using 'Delphi 12 Update 1,' I created a simple project. The purpose of the project was to create an 'ini' file (via the TIniFile component) made up of ten sections. Each section holding forty-five keys. Each key having a random integer (between 0 and 999) as value. When the executable is run under an older 32-bit Windows OS, the creation of the 'ini' takes less than two hundred milliseconds. However, when the same executable is run under a newer 64-bit Windows OS (such as 'Windows 10'), the creation of the 'ini' is considerably slower. Indeed, it took almost three seconds for the file to be created. As anybody else experienced this 'new' behavior? I am saying 'new' behavior because prior to February 2025, the execution times were almost identical between the older OS and the newer one. Edited Wednesday at 08:02 PM by Jean_D Share this post Link to post
Remy Lebeau 1494 Posted Wednesday at 10:15 PM (edited) Must be something specific on your PC. Using Delphi 12.2 Patch 2 on Windows 10 64-bit, when I create an INI file with the specifications you have described, it takes only 150ms with TIniFile. Switch to TMemIniFile and that drops to under 5ms. Edited Wednesday at 10:17 PM by Remy Lebeau Share this post Link to post
Jean_D 1 Posted Wednesday at 11:52 PM May I ask which anti-virus software are you using? I am using 'Microsoft Defender Antivirus'. I have noticed that, if I turn off 'Microsoft Defender Antivirus,' my speed issue disappear. Share this post Link to post
Remy Lebeau 1494 Posted yesterday at 04:26 AM 4 hours ago, Jean_D said: May I ask which anti-virus software are you using? I use AVG. 4 hours ago, Jean_D said: I have noticed that, if I turn off 'Microsoft Defender Antivirus,' my speed issue disappear. You might consider adding an exception to it for your data folder. Share this post Link to post
Jean_D 1 Posted 22 hours ago You are correct. Adding an exception does indeed remove the slowness. It is strange though that the same program written in C++ via Visual Studio does not experience the slowness (without adding an exception). Share this post Link to post
Stefan Glienke 2034 Posted 22 hours ago I bet the C++ code does not do the same as TIniFile in Delphi which calls WritePrivateProfileString for every entry. Share this post Link to post
Jean_D 1 Posted 20 hours ago The C++ code might not be 100% identical to the Delphi one. But its essence is the same. void CreateIniFile(const char* iniFileName) { // Get the directory of the executable std::wstring exeDir = GetExecutableDirectory(); if (exeDir.empty()) { return; // Exit if we couldn't get the executable directory } // Combine the executable directory with the INI file name std::wstring iniFilePath = exeDir + L"\\" + std::wstring(iniFileName, iniFileName + strlen(iniFileName)); // Define the sections const char* sections[] = { "Section1", "Section2", "Section3", "Section4", "Section5", "Section6" }; // Convert iniFile to wide-character string (LPCWSTR) std::wstring wIniFile = iniFilePath; // Loop through the sections for (int i = 0; i < 6; ++i) { std::string section = sections[i]; std::wstring wsection; ConvertToWideChar(section, wsection); // Generate a random number of keys between 40 and 50 for this section int numKeys = RandomNumber(40, 50); // Loop through the keys in each section for (int j = 1; j <= numKeys; ++j) { // Create a key name (e.g., Key1, Key2, ... KeyN) std::string key = "Key" + std::to_string(j); std::wstring wkey; ConvertToWideChar(key, wkey); // Create an integer value for the key (e.g., 123, 456, ...) int value = RandomNumber(1, 1000); // You can change the range as needed std::string valueStr = std::to_string(value); std::wstring wvalue; ConvertToWideChar(valueStr, wvalue); // Write the key-value pair to the INI file BOOL result = WritePrivateProfileString(wsection.c_str(), wkey.c_str(), wvalue.c_str(), wIniFile.c_str()); if (!result) { std::cout << "Error writing key " << key << " to section " << section << std::endl; } } } std::wcout << L"INI file created successfully at " << iniFilePath << std::endl; } Share this post Link to post
Remy Lebeau 1494 Posted 18 hours ago (edited) 1 hour ago, Jean_D said: The C++ code might not be 100% identical to the Delphi one. But its essence is the same. Hard to say when you didn't show the Delphi code to compare. On a side note... 1 hour ago, Jean_D said: // Combine the executable directory with the INI file name std::wstring iniFilePath = exeDir + L"\\" + std::wstring(iniFileName, iniFileName + strlen(iniFileName)); That is not the correct way to convert a char* string to a std::wstring. That just makes a copy of each char as-is to wchar_t, which does not actually translate the characters from one encoding to another. You need MultiByteForWideChar() or equivalent for that task to avoid data loss/corruption. Since you have a ConvertToWideChar() function, why not use it? Hopefully it does a proper conversion: std::wstring iniFilePath; ConvertToWideChar(exeDir + "\\" + std::string(iniFileName), iniFilePath); Though, why does ConvertToWideChar() take a std::wstring variable as an output parameter, instead of returning the std::wstring? If it did that instead, you could eliminate your wIniFile, wsection, and wkey variables. 1 hour ago, Jean_D said: // Define the sections const char* sections[] = { "Section1", "Section2", "Section3", "Section4", "Section5", "Section6" }; Why char* here? You are converting from char* to std::string to std::wstring, which is a bit overkill. You could have the array store wchar_t* instead, and get rid of the std::string and std::wstring variables, since WritePrivateProfileStringW() takes wchar_t* strings. 1 hour ago, Jean_D said: // Create a key name (e.g., Key1, Key2, ... KeyN) std::string key = "Key" + std::to_string(j); std::wstring wkey; ConvertToWideChar(key, wkey); // Create an integer value for the key (e.g., 123, 456, ...) int value = RandomNumber(1, 1000); // You can change the range as needed std::string valueStr = std::to_string(value); std::wstring wvalue; ConvertToWideChar(valueStr, wvalue); If you use std::to_wstring() instead of std::to_string(), you can get rid of these std::string variables and ConvertToWideChar() calls. Edited 18 hours ago by Remy Lebeau Share this post Link to post
Jean_D 1 Posted 17 hours ago 33 minutes ago, Remy Lebeau said: Hard to say when you didn't show the Delphi code to compare. Fair point, here is the Delphi code: procedure TForm1.Button1Click(Sender: TObject); var iCnt: Byte; iCpt: Byte; iSection: String; iIniFile: TIniFile; iIdentifier: String; begin iIniFile := TIniFile.Create(ChangeFileExt(Application.ExeName, '.ini')); for iCnt := 1 to 6 do begin iSection := 'Tab #' + IntToStr(iCnt); for iCpt := 1 to 45 do begin iIdentifier := 'Key #' + IntToStr(iCpt); iIniFile.WriteInteger(iSection, iIdentifier, Random(999)); end; end; iIniFile.Free; end; 34 minutes ago, Remy Lebeau said: On a side note... Thanks for all the pointers. In terms of Visual Studio C++ (or C++ in general), I have very little knowledge. I used AI to help me write the code. The code that I posted is the code that I got with its help. I will use your inputs to improve it and learn from it. Share this post Link to post