PHP中如何将特殊格式文本型DAT文件转为关联数组
嘿,针对你这个特殊格式的DAT文件转PHP关联数组的需求,我刚好有个靠谱的解决方案,咱们一步步来:
解决方案思路
这个文件的格式是按[数字]作为条目分隔,每个条目里是键=值的键值对(值可能包含空格,比如Name=Standard 1),所以不能用简单的逐行读取+explode,得用正则来精准匹配:
- 先把整个文件内容读进来,一次性分割出每个
[数字]开头的完整条目 - 对每个条目,再提取里面的所有键值对,组装成子关联数组
- 最后把所有子数组按
[数字]里的序号作为键,整合到最终的大数组里
完整代码实现
// 读取DAT文件内容 $fileContent = file_get_contents('your_file.dat'); if (!$fileContent) { die("无法读取文件,请检查文件路径是否正确"); } // 匹配所有[数字]开头的条目 preg_match_all('/\[(\d+)\]\s+(.*?)(?=\s*\[\d+\]|$)/s', $fileContent, $matches); $result = []; // 遍历每个匹配到的条目 foreach ($matches[1] as $index => $entryKey) { $entryData = $matches[2][$index]; // 提取当前条目里的所有键值对(处理值含空格的情况) preg_match_all('/(\w+)=([^=]+?)(?=\s+\w+=|\s*$)/', $entryData, $kvPairs); $entryArray = []; foreach ($kvPairs[1] as $kvIndex => $key) { // 去掉值前后可能存在的空格,保留值中间的空格 $entryArray[$key] = trim($kvPairs[2][$kvIndex]); } $result[$entryKey] = $entryArray; } // 打印结果看看(或者按你的需求使用这个数组) print_r($result);
代码细节解释
- 读取文件:用
file_get_contents一次性读取,比逐行读取更适合这种跨多行的条目格式(如果你的文件条目是跨多行的也能处理,因为正则加了s修饰符让.匹配换行符) - 分割条目:正则
/\[(\d+)\]\s+(.*?)(?=\s*\[\d+\]|$)/s的作用:\[(\d+)\]:匹配[数字],并捕获数字作为条目键\s+:匹配条目开头的空格(.*?):非贪婪匹配条目内容,直到遇到下一个[数字]或者文件结尾(?=\s*\[\d+\]|$):正向预查,确保内容截止到下一个条目开头或者文件末尾
- 提取键值对:正则
/(\w+)=([^=]+?)(?=\s+\w+=|\s*$)/的作用:(\w+):匹配键名(字母、数字、下划线)并捕获=:匹配分隔符([^=]+?):非贪婪匹配值,直到遇到下一个键=或者条目结尾(避免把后面的键值对也当成值)(?=\s+\w+=|\s*$):正向预查,确保值截止到下一个键值对开头或者条目末尾
- 组装数组:把每个条目的键值对整理成子数组,然后按条目序号作为键存入最终数组
用这个代码处理你给出的示例内容,最终会得到这样的关联数组:
Array ( [0] => Array ( [FirstRideOn] => 43169.5701090972 [Laps] => 4591 [LastRideOn] => 43224.7924173611 [Name] => Standard 1 [Nr] => 1 [ResetDate] => 0 [RunningTime] => 2481 [Runs] => 233 [TranNr] => 7435191 ) [1] => Array ( [FirstRideOn] => 43149.5406271644 [Laps] => 5528 [LastRideOn] => 43224.7616565972 [Name] => Standard 2 [Nr] => 2 [ResetDate] => 0 [RunningTime] => 2957 [Runs] => 292 [TranNr] => 8377256 ) )
内容的提问来源于stack exchange,提问作者danielquatz
相关产品推荐
相关产品推荐

