Reading SPWLA file with Regex

The 3 methods for extracting data are:

  • Looping over the file and applying string methods, etc. >>> this is a naive approach, very fiddly.
  • Using regex to extract everything at once. >>> This notebook.
  • Using a parser. >>> I don't think I'm clever enough for this.

In [1]:
!head -24 ../data/core_analysis_example.spwla


10     2                                                                                                                       
    9999/9-9                                Norway                                            9Sep99
    Weatherford-Labs
15    10   10
          1507      1602  2031   0Weatherford-Labs    Nitrogen Permeability, Hor.
          1512      1602  2031   0Weatherford-Labs    Klinkenberg corrected gas perm, Hor.
          1510      1602  2031   0Weatherford-Labs    Nitrogen Permeability, Vert.
          1515      1602  2031   0Weatherford-Labs    Klinkenberg corrected gas perm, Vert.
          1402      1211  3084   0Weatherford-Labs    Porosity, Horizontal PLUG
          1403      1211  3084   0Weatherford-Labs    Porosity, Vertical PLUG
          1401      1212  3084   0Weatherford-Labs    Porosity, Summation
          1302      1103  3085   0Weatherford-Labs    CORE Oil Saturation
          1301      1103  3085   0Weatherford-Labs    CORE Water Saturation
          2451      1201  1086   0Weatherford-Labs    Grain Density, Hor.
20     1
        0.00     0.00  1918.00  1983.72  0.0  1
30     1
     1918.95     0.00   1.11
40     1   10
     -1002.00000 -1002.00000 -1002.00000 -1002.00000 -1002.00000    18.44722 -1002.00000    14.78718 -1002.00000 -1002.00000
30     1
     1919.95     0.00   2.11
40     1   10
     -1002.00000 -1002.00000 -1002.00000 -1002.00000 -1002.00000    17.06246 -1002.00000    18.06427 -1002.00000 -1002.00000

Observations

  • Some lines are 128 characters wide
  • Some of the data is unidentifiable
  • This is probably a job for striplog
  • The info after the record type (10, 15, 20, 30, etc) seems to be the number of lines (and fields per line, perhaps) in that record, which is redundant information (can just read until the next record type flag)

Regex SPWLA file

From this StackOverflow question.


In [205]:
s = """10     2                                                                                                                       
    9999/9-9                                Norway                                            9Sep99
    Weatherford-Labs
15    10   10
          1507      1602  2031   0Weatherford-Labs    Nitrogen Permeability, Hor.
          1512      1602  2031   0Weatherford-Labs    Klinkenberg corrected gas perm, Hor.
          1510      1602  2031   0Weatherford-Labs    Nitrogen Permeability, Vert.
          1515      1602  2031   0Weatherford-Labs    Klinkenberg corrected gas perm, Vert.
          1402      1211  3084   0Weatherford-Labs    Porosity, Horizontal PLUG
          1403      1211  3084   0Weatherford-Labs    Porosity, Vertical PLUG
          1401      1212  3084   0Weatherford-Labs    Porosity, Summation
          1302      1103  3085   0Weatherford-Labs    CORE Oil Saturation
          1301      1103  3085   0Weatherford-Labs    CORE Water Saturation
          2451      1201  1086   0Weatherford-Labs    Grain Density, Hor.
20     1
        0.00     0.00  1918.00  1983.72  0.0  1
30     1
     1918.95     0.00   1.11
40     1   10
     -1002.00000 -1002.00000 -1002.00000 -1002.00000 -1002.00000    18.44722 -1002.00000    14.78718 -1002.00000 -1002.00000
30     1
     1919.95     0.00   2.11
40     1   10
     -1002.00000 -1002.00000 -1002.00000 -1002.00000 -1002.00000    17.06246 -1002.00000    18.06427 -1002.00000 -1002.00000
     """

In [207]:
import re

# Not using this one.
# rx_fields = re.compile(r'''
#     ^
#     15\s+?\d+?\s+?\d+?\n
#     (?P<fields>[\s\S]+?)
#     (?=^[^1]|\Z)
# ''', re.MULTILINE | re.VERBOSE)

rx_fields = re.compile(r'''
    ^
    \s+?\d+?\s+?\d+?\s+?\d+?\s+?0\S+?\s+?(?P<field>[\w\d][- ,.\w\d]+?)\n
''', re.MULTILINE | re.VERBOSE)

rx_depth = re.compile(r'''
    ^
    30\s+?1\n
    \s+?(?P<depth>[.\d]+?)[ \t]+?[.\d]+?[ \t]+?(?P<seq>[.\d]+?)\n
    (?P<record>[\s\S]+?)
    (?=^30|\Z)
''', re.MULTILINE | re.VERBOSE)

rx_data = re.compile(r'''
    ^
    (?:36\s+?1\s+?1\n
    \s+?(?P<descr>.+?)\n)?
    40\s+?1\s+?\d+?\n
    \s+?(?P<data>[- .\d]+?)\n
''', re.MULTILINE | re.VERBOSE)

In [208]:
import pandas as pd
import numpy as np

def parse(s, null=-999.25): 
    
    records = (field.group('field') for field in rx_fields.finditer(s))

    result = (
              (
                float(record.group('depth')),
                record.group('seq'),
                data.group('descr'),
                *[float(x) for x in data.group('data').split()]
              )
               for record in rx_depth.finditer(s)
               for data in rx_data.finditer(record.group('record'))
    )

    columns = ['depth', 'seq', 'descr'] + list(records)
    
    df = pd.DataFrame(result, columns=columns)
    df = df.replace(null, np.nan)

    return df

In [209]:
parse(data, null=-1002)


Out[209]:
depth seq descr Nitrogen Permeability, Hor. Klinkenberg corrected gas perm, Hor. Nitrogen Permeability, Vert. Klinkenberg corrected gas perm, Vert. Porosity, Horizontal PLUG Porosity, Vertical PLUG Porosity, Summation CORE Oil Saturation CORE Water Saturation Grain Density, Hor.
0 1918.95 1.11 None NaN NaN NaN NaN NaN 18.44722 NaN 14.78718 NaN NaN
1 1919.95 2.11 None NaN NaN NaN NaN NaN 17.06246 NaN 18.06427 NaN NaN
2 1920.95 3.11 None NaN NaN NaN NaN NaN 19.58139 NaN 19.01052 NaN NaN
3 1921.95 4.11 None NaN NaN NaN NaN NaN 18.32791 NaN 17.92610 NaN NaN
4 1922.95 5.11 None NaN NaN NaN NaN NaN 16.67100 NaN 20.77644 NaN NaN
5 1923.95 6.11 None NaN NaN NaN NaN NaN 15.49629 NaN 24.60543 NaN NaN
6 1924.95 7.11 None NaN NaN NaN NaN NaN 18.28268 NaN 12.88050 NaN NaN
7 1925.95 8.11 None NaN NaN NaN NaN NaN 18.43782 NaN 13.75609 NaN NaN
8 1926.95 9.11 None NaN NaN NaN NaN NaN 17.31157 NaN 14.66162 NaN NaN
9 1927.95 10.11 None NaN NaN NaN NaN NaN 19.34322 NaN 13.08335 NaN NaN
10 1928.95 11.11 None NaN NaN NaN NaN NaN 18.61451 NaN 18.12203 NaN NaN
11 1929.95 12.11 None NaN NaN NaN NaN NaN 16.17023 NaN 14.21380 NaN NaN
12 1930.95 13.11 None NaN NaN NaN NaN NaN 18.13845 NaN 11.11148 NaN NaN
13 1931.95 14.11 None NaN NaN NaN NaN NaN 13.27176 NaN 12.31301 NaN NaN
14 1932.95 15.11 None NaN NaN NaN NaN NaN 10.50659 NaN 19.31734 NaN NaN
15 1933.95 16.11 None NaN NaN NaN NaN NaN 16.97168 NaN 21.41411 NaN NaN
16 1934.95 17.11 None NaN NaN NaN NaN NaN 16.40207 NaN 43.12578 NaN NaN
17 1935.95 18.11 None NaN NaN NaN NaN NaN 22.72481 NaN 55.43833 NaN NaN
18 1936.95 19.11 None NaN NaN NaN NaN NaN 18.41375 NaN 59.59112 NaN NaN
19 1937.95 20.11 None NaN NaN NaN NaN NaN 18.85675 NaN 50.40101 NaN NaN
20 1938.95 21.11 None NaN NaN NaN NaN NaN 17.93774 NaN 44.58358 NaN NaN
21 1940.95 22.11 None NaN NaN NaN NaN NaN 18.46985 NaN 49.18243 NaN NaN
22 1941.95 23.11 None NaN NaN NaN NaN NaN 14.96825 NaN 47.84605 NaN NaN
23 1942.95 24.11 None NaN NaN NaN NaN NaN 19.11698 NaN 47.18030 NaN NaN
24 1943.95 25.11 None NaN NaN NaN NaN NaN 17.74624 NaN 47.80520 NaN NaN
25 1944.95 26.11 None NaN NaN NaN NaN NaN 11.29837 NaN 46.18566 NaN NaN
26 1945.95 27.11 None NaN NaN NaN NaN NaN 19.35403 NaN 45.72604 NaN NaN
27 1946.95 28.11 None NaN NaN NaN NaN NaN 15.65132 NaN 47.17111 NaN NaN
28 1947.95 29.11 None NaN NaN NaN NaN NaN 13.45465 NaN 40.23944 NaN NaN
29 1948.95 30.11 None NaN NaN NaN NaN NaN 16.54562 NaN 34.87458 NaN NaN
... ... ... ... ... ... ... ... ... ... ... ... ... ...
298 1976.50 235 Sst.Lt-gry.VF-gr.VW-Consol.VW-srt.Lam.w-C,C... 0.093 0.055 0.017 0.009 11.42335 NaN NaN NaN NaN 2.65691
299 1976.75 236 Sst.Lt-gry.VF-gr.VW-Consol.VW-srt.Lam.w-C,C... 0.166 0.102 0.025 0.013 8.34043 NaN NaN NaN NaN 2.63852
300 1977.02 237 Sst.Lt-gry.VF-gr.VW-Consol.VW srt.w-C,Cl,Mi... 0.239 0.149 0.112 0.067 13.71619 NaN NaN NaN NaN 2.66542
301 1977.25 238 Sst.Lt-gry.VF-gr.VW-Consol.VW srt.Lam.w-C,C... 0.194 0.120 0.024 0.013 12.92918 NaN NaN NaN NaN 2.65561
302 1977.51 239 Sst.Lt-gry.VF/F-gr.VW-Consol.W srt.Fis.w-Cl... 6.642 5.095 4.422 3.352 15.37053 NaN NaN NaN NaN 2.66011
303 1977.77 240 Sst.Lt-gry.VF-gr.VW-Consol.VW srt.Fis.w-C,C... 0.959 0.651 0.227 0.141 12.76678 NaN NaN NaN NaN 2.65316
304 1978.32 241 Sst.Lt-gry.VF/M-gr.VW Consol.M srt.Lam.Frac... 0.000 0.000 0.132 0.080 11.33350 NaN NaN NaN NaN 2.64860
305 1978.50 242 Sst.Lt-gry.VF/F-gr.VW Consol.W srt.w-tr Cal... 40.739 35.064 20.687 17.017 17.51168 NaN NaN NaN NaN 2.68379
306 1978.70 243 Sst.Lt-gry.VF/F-gr.VW Consol.VW-srt.Lam.w-C... 0.098 0.058 0.109 0.065 10.33719 NaN NaN NaN NaN 2.66098
307 1978.88 244 Slsty Sst.MLt-gry.VF-gr.VW Consol.VW-srt.La... 0.107 0.064 0.074 0.043 11.68598 NaN NaN NaN NaN 2.66552
308 1979.02 245 Sst.Yelsh-gry.VF/M-gr.VW Consol.M-srt.Lam.F... 6.085 4.677 7.569 6.100 11.51438 NaN NaN NaN NaN 2.65606
309 1979.25 246 Sst.VLt-gry.F/M-gr.Sbang.W-cmt.M-srt.w-tr Cl. 1722.764 1651.775 486.432 454.547 20.38721 NaN NaN NaN NaN 2.64458
310 1979.46 247 Sst.Lt-gry.VF-gr.VW Consol.VW-srt.Fis.w-C,C... 0.995 0.676 0.084 0.049 11.05768 NaN NaN NaN NaN 2.64788
311 1979.75 248 Sst.Lt-gry.VF/F-gr.VW Consol.W-srt.Thin Lam... 9.106 7.117 11.609 9.429 13.00959 NaN NaN NaN NaN 2.69492
312 1980.02 249 Sst.Lt-gry.VF/F-gr.Sbang.W-cmt.W-srt.w-ltl ... 558.779 523.998 596.169 559.849 22.93377 NaN NaN NaN NaN 2.66242
313 1980.23 250 Sst.Lt-gry.VF/F-gr.Sbang.W-cmt.W-srt.w-ltl ... 559.596 524.704 439.650 409.777 22.26690 NaN NaN NaN NaN 2.65279
314 1980.50 251 Sst.Lt-gry.VF/F-gr.Sbang.W-cmt.W-srt.w-ltl ... 420.865 391.804 147.913 133.392 21.65629 NaN NaN NaN NaN 2.65754
315 1980.75 252 Sst.Lt-gry.VF/C-gr.Sbang.W-cmt.P-srt.w-ltl ... 909.761 862.228 219.213 200.279 23.23437 NaN NaN NaN NaN 2.65884
316 1981.02 253 Sst.Lt-gry.VF/M-gr.Sbang.W-cmt.M-srt.Irr La... 61.320 53.515 14.042 11.348 16.89518 NaN NaN NaN NaN 2.68712
317 1981.25 254 Sst.Lt-gry.VF/F-gr.Sbang.W-cmt.W-srt.w-tr C... 151.734 137.053 183.173 166.378 17.80920 NaN NaN NaN NaN 2.66355
318 1981.51 255 Sst.Lt-gry.VF/M-gr.Sbang.W-cmt.M-srt.w-Cl,Mic. 1.178 0.809 0.237 0.148 11.41745 NaN NaN NaN NaN 2.65450
319 1981.75 256 Sst.Lt-gry.VF/C-gr.Sbang.W-cmt.P-srt.w-Cl,Mic. 3.772 2.815 2.247 1.757 16.10870 NaN NaN NaN NaN 2.65847
320 1982.12 257 Sst.Lt-gry.F/M-gr.Sbang.W-cmt.M-srt.tr Mtrx... 38.395 32.908 0.219 0.136 14.17604 NaN NaN NaN NaN 2.64581
321 1982.35 258 Sst.Lt-gry.VF/M-gr.Sbang.W-cmt.M-srt.w-llt ... 217.808 198.934 260.715 239.469 20.34436 NaN NaN NaN NaN 2.67607
322 1982.57 259 Sst.Lt-gry.VF/VC-gr.Sbang.W-cmt.VP-srt.Mtrx... 91.605 81.311 628.956 591.362 17.65817 NaN NaN NaN NaN 2.66311
323 1982.79 260 Sst.Lt-gry.VF/VC-gr.Gran.Sbang.W-cmt.VP-srt... 1823.535 1750.044 628.296 590.727 21.23241 NaN NaN NaN NaN 2.64861
324 1983.02 261 Sst.Lt-gry.VF/VC-gr.Gran.Sbang.W-cmt.VP-srt... 517.099 484.015 142.276 128.133 19.07649 NaN NaN NaN NaN 2.65108
325 1983.24 262 Sst.Lt-gry.VF/VC-gr.Sbang.W-cmt.VP-srt.w-lt... 650.344 612.018 132.574 119.098 15.08463 NaN NaN NaN NaN 2.65493
326 1983.44 263 Sst.Lt Olv-gry.VF/F-gr.Sbang.W-cmt.W-srt.La... 0.000 0.000 1.820 1.283 9.44161 NaN NaN NaN NaN 2.76367
327 1983.70 264 Sst.Yelsh-gry.VF/F-gr.Sbang.W-cmt.W-srt.Lam... 0.000 0.000 0.040 0.022 7.41085 NaN NaN NaN NaN NaN

328 rows × 13 columns

This has been dropped into ../gio/gio.py as read_spwla().


In [ ]: