Read all ini file values with GetPrivateProfileString

浪尽此生 提交于 2019-12-03 02:37:47
leon22

Possible solution:

[DllImport("kernel32.dll")]
private static extern int GetPrivateProfileSection(string lpAppName, byte[] lpszReturnBuffer, int nSize, string lpFileName);

private List<string> GetKeys(string iniFile, string category)
{

    byte[] buffer = new byte[2048];

    GetPrivateProfileSection(category, buffer, 2048, iniFile);
    String[] tmp = Encoding.ASCII.GetString(buffer).Trim('\0').Split('\0');

    List<string> result = new List<string>();

    foreach (String entry in tmp)
    {
        result.Add(entry.Substring(0, entry.IndexOf("=")));
    }

    return result;
}

I believe there's also GetPrivateProfileSection() that could help, but I agree with Zenwalker, there are libraries that could help with this. INI files aren't that hard to read: sections, key/value and comments is pretty much it.

Why dont you use IniReader library to read INI files?? its easier and faster that way.

These routines will read an entire INI section, and either return the section as a collection of raw strings where each entry is a single line in the INI file (useful if you're using the INI structure but don't necessarily have an =), and another that returns a collection of keyvalue pairs for all of the entries in the section.

    [DllImport("kernel32.dll")]
    public static extern uint GetPrivateProfileSection(string lpAppName, IntPtr lpReturnedString, uint nSize, string lpFileName);

    // ReSharper disable once ReturnTypeCanBeEnumerable.Global
    public static string[] GetIniSectionRaw(string section, string file) {
        string[] iniLines;
        GetPrivateProfileSection(section, file, out iniLines);
        return iniLines;
    }

    /// <summary> Return an entire INI section as a list of lines.  Blank lines are ignored and all spaces around the = are also removed. </summary>
    /// <param name="section">[Section]</param>
    /// <param name="file">INI File</param>
    /// <returns> List of lines </returns>
    public static IEnumerable<KeyValuePair<string, string>> GetIniSection(string section, string file) {
        var result = new List<KeyValuePair<string, string>>();
        string[] iniLines;
        if (GetPrivateProfileSection(section, file, out iniLines)) {
            foreach (var line in iniLines) {
                var m = Regex.Match(line, @"^([^=]+)\s*=\s*(.*)");
                result.Add(m.Success
                               ? new KeyValuePair<string, string>(m.Groups[1].Value, m.Groups[2].Value)
                               : new KeyValuePair<string, string>(line, ""));
            }
        }

        return result;
    }
Dim MyString    As String = String.Empty
Dim BufferSize As Integer = 1024 
Dim PtrToString As IntPtr = IntPtr.Zero
Dim RetVal As Integer
RetVal = GetPrivateProfileSection(SectionName, PtrToString, BufferSize, FileNameAndPah)

If our function call succeeds, we will get the result in PtrToString memory address and RetVal will contain the length of the string in PtrToString. Else if this function failed due to the lack of enough BufferSize Then RetVal will contain BufferSize - 2. So we can check it and call this function again with larger BufferSize.

'Now, here is how we can get the string from memory address.

MyString = Marshal.PtrToStringAuto(PtrToString, RetVal - 1)

'Here i use " RetVal - 1 " to avoid the extra null string.

' Now, we need to split the string where null chars coming.

Dim MyStrArray() As String = MyString.Split(vbNullChar)

So this array contains all your keyvalue pair in that specific section. And dont forget to free up the memory

Marshal.FreeHGlobal(PtrToString)
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!