A documentação oficial está hospedada em readthedocs.
Segyio é uma pequena biblioteca C licenciada LGPL para fácil interação com dados sísmicos formatados em SEG-Y e Seismic Unix, com ligações de linguagem para Python e Matlab. Segyio é uma tentativa de criar uma biblioteca fácil de usar, incorporável e voltada para a comunidade para aplicações sísmicas. Os recursos são adicionados conforme necessário; sugestões e contribuições de todos os tipos são muito bem-vindas.
Para acompanhar os desenvolvimentos e recursos mais recentes, consulte o changelog. Para escrever código à prova de futuro, consulte as alterações significativas planejadas.
Quando o segyio estiver construído e instalado, você estará pronto para começar a programar! Confira o tutorial, exemplos, programas de exemplo e cadernos de exemplo. Para referência técnica com exemplos e pequenas receitas, leia a documentação. Os documentos da API também estão disponíveis com pydoc - inicie seu interpretador Python favorito e digite help(segyio)
, que deve se integrar bem com IDLE, pycharm e outras ferramentas Python.
import segyio
import numpy as np
with segyio . open ( 'file.sgy' ) as f :
for trace in f . trace :
filtered = trace [ np . where ( trace < 1e-2 )]
Veja os exemplos para mais.
Uma cópia do segyio está disponível como binários pré-construídos e código-fonte:
apt install python3-segyio
pip install segyio
git clone https://github.com/statoil/segyio
Para construir o segyio você precisa de:
Para construir a documentação, você também precisa do sphinx
Para compilar e instalar o segyio, execute as seguintes ações em seu console:
git clone https://github.com/equinor/segyio
mkdir segyio/build
cd segyio/build
cmake .. -DCMAKE_BUILD_TYPE=Release -DBUILD_SHARED_LIBS=ON
make
make install
make install
deve ser feito como root para uma instalação do sistema; se você deseja instalar em seu diretório inicial, adicione -DCMAKE_INSTALL_PREFIX=~/
ou algum outro diretório apropriado, ou make DESTDIR=~/ install
. Certifique-se de que seu ambiente seja compatível com locais de instalação não padrão (PYTHONPATH, LD_LIBRARY_PATH e PATH).
Se você tiver várias instalações do Python ou quiser usar algum interpretador alternativo, você pode ajudar o cmake a encontrar o correto passando -DPYTHON_EXECUTABLE=/opt/python/binary
junto com o prefixo de instalação e o tipo de compilação.
Para construir as ligações matlab, invoque CMake com a opção -DBUILD_MEX=ON
. Em alguns ambientes, os binários do Matlab estão em um local não padrão; nesse caso, você precisa ajudar o CMake a encontrar os binários do Matlab passando -DMATLAB_ROOT=/path/to/matlab
.
É recomendado compilar no modo de depuração para obter mais avisos e incorporar símbolos de depuração nos objetos. Substituir Debug
por Release
em CMAKE_BUILD_TYPE
é suficiente.
Os testes estão localizados nos diretórios language/tests e é altamente recomendado que os novos recursos adicionados sejam demonstrados quanto à correção e contração adicionando um teste. Todos os testes podem ser executados invocando ctest
. Sinta-se à vontade para usar os testes já escritos como guia.
Após construir o segyio você pode executar os testes com ctest
, executados no diretório build.
Observe que para executar os exemplos Python você precisa informar ao seu ambiente onde encontrar a biblioteca Python. Ele pode ser instalado como usuário ou adicionando a biblioteca segyio/build/python ao seu pythonpath.
Todo o código neste tutorial pressupõe que segyio foi importado e que numpy está disponível como np.
import segyio
import numpy as np
Este tutorial pressupõe que você esteja familiarizado com Python e numpy. Para uma atualização, confira o tutorial python e o início rápido numpy
A abertura de um arquivo para leitura é feita com a função segyio.open
e usada idiomaticamente com gerenciadores de contexto. Usando a instrução with
, os arquivos são fechados corretamente mesmo no caso de exceções. Por padrão, os arquivos são abertos somente leitura.
with segyio . open ( filename ) as f :
...
Open aceita várias opções (para uma referência mais abrangente, verifique a docstring da função open com help(segyio.open)
. A opção mais importante é o segundo argumento posicional (opcional). Para abrir um arquivo para escrita, faça segyio.open(filename, 'r+')
, da função C fopen
.
Os arquivos podem ser abertos no modo não estruturado , passando segyio.open
os argumentos opcionais strict=False
, caso em que não estabelecer estrutura (números embutidos, números cruzados etc.) não é um erro, e ignore_geometry=True
, nesse caso segyio nem tentarei definir esses atributos internos.
O objeto de arquivo segy possui vários atributos públicos que descrevem esta estrutura:
f.ilines
Números embutidos inferidosf.xlines
Números de linhas cruzadas inferidosf.offsets
Números de deslocamentos inferidosf.samples
Deslocamentos de amostra inferidos (frequência e atraso de tempo de gravação)f.unstructured
Verdadeiro se não estruturado, Falso se estruturadof.ext_headers
O número de cabeçalhos textuais estendidos Se o arquivo for aberto não estruturado , todas as propriedades da linha serão None
.
No segyio, os dados são recuperados e gravados através dos chamados modos . Os modos são matrizes abstratas ou esquemas de endereçamento e alteram o significado dos nomes e índices. Todos os modos são propriedades no objeto de manipulação de arquivo, suportam a função len
e as leituras e gravações são feitas por meio de f.mode[]
. As gravações são feitas com atribuição. Os modos suportam fatiamento de array inspirado em numpy. Os seguintes modos estão disponíveis:
trace
O modo de rastreamento oferece endereçamento bruto de rastreamentos conforme eles são dispostos no arquivo. Este, junto com header
, é o único modo disponível para arquivos não estruturados. Os rastreamentos são enumerados 0..len(f.trace)
.
A leitura de um rastreamento produz um ndarray
numpy e a leitura de vários rastreamentos produz um gerador de ndarray
s. A semântica do gerador é usada e o mesmo objeto é reutilizado, portanto, se você quiser armazenar em cache ou endereçar dados de rastreamento posteriormente, deverá copiar explicitamente.
> >> f . trace [ 10 ]
> >> f . trace [ - 2 ]
> >> f . trace [ 15 : 45 ]
> >> f . trace [: 45 : 3 ]
header
Com comportamento de endereçamento semelhante a trace
, o acesso a itens produz objetos de cabeçalho em vez de numpy ndarray
s. Cabeçalhos são objetos semelhantes a dict, onde as chaves são inteiros, chaves sísmicas no estilo unix (no módulo segyio.su) e enums segyio (segyio.TraceField).
Os valores do cabeçalho podem ser atualizados atribuindo-lhe um ditado semelhante, e as chaves não presentes no lado direito da atribuição não são modificadas .
> >> f . header [ 5 ] = { segyio . su . tracl : 10 }
> >> f . header [ 5 ]. items ()
> >> f . header [ 5 ][ 25 , 37 ] # read multiple values at once
iline
, xline
Esses modos gerarão um erro se o arquivo não estiver estruturado. Eles consideram os argumentos para []
como as chaves das respectivas linhas. Os números das linhas estão sempre aumentando, mas podem ter espaçamentos arbitrários e desiguais. Os nomes válidos podem ser encontrados nas propriedades ilines
e xlines
.
Tal como acontece com os rastreamentos, obter uma linha produz um ndarray
e uma fatia de linhas produz um gerador de ndarray
s. Ao usar fatias com uma etapa, alguns itens intermediários podem ser ignorados se não corresponderem à etapa, ou seja, fazer f.line[1:10:3]
em um arquivo com linhas [1,2,3,4,5]
é equivalente a procurar 1, 4, 7
e encontrar [1,4]
.
Ao trabalhar com um arquivo pré-empilhado 4D, o primeiro deslocamento é lido implicitamente. Para acessar um intervalo diferente ou de deslocamentos, use índices ou intervalos separados por vírgula, como: f.iline[120, 4]
.
fast
, slow
Esses são aliases para iline
e xline
, determinados pela forma como os rastreamentos são dispostos. Para arquivos classificados in-line, fast
resultaria iline
.
depth_slice
A fatia de profundidade é um corte horizontal em profundidade em todo o arquivo. Os valores produzidos são ndarray
se geradores de matrizes.
gather
A gather
é a interseção de uma linha embutida e uma linha cruzada, uma coluna vertical da pesquisa e, a menos que um único deslocamento seja especificado, retorna um deslocamento x amostras ndarray
. Na presença de intervalos, ele retorna um gerador desses ndarray
s.
text
O modo de text
é uma matriz de cabeçalhos textuais, onde text[0]
é o cabeçalho textual obrigatório padrão e 1..n
são os cabeçalhos estendidos opcionais.
Os cabeçalhos de texto são retornados como blobs semelhantes a bytes de 3.200 bytes, conforme estão no arquivo. A função segyio.tools.wrap
pode criar uma versão orientada a linhas desta string.
bin
Os valores do cabeçalho binário de todo o arquivo com uma interface semelhante a um dict. Comporta-se como o modo header
, mas sem indexação.
> >> for line in f . iline [: 2430 ]:
... print ( np . average ( line ))
> >> for line in f . xline [ 2 : 10 ]:
... print ( line )
> >> for line in f . fast [:: 2 ]:
... print ( np . min ( line ))
> >> for factor , offset in enumerate ( f . iline [ 10 , :]):
... offset *= factor
print ( offset )
> >> f . gather [ 200 , 241 , :]. shape
> >> text = f . text [ 0 ]
> >> type( text )
< type 'bytes' >
> >> f . trace [ 10 ] = np . zeros ( len ( f . samples ))
Mais exemplos e receitas podem ser encontrados na documentação help(segyio)
e na seção de exemplos.
Segyio não tenta necessariamente ser o fim de todas as interações SEG-Y; em vez disso, pretendemos diminuir a barreira à interação com arquivos SEG-Y para incorporação, novos aplicativos ou programas independentes.
Além disso, o objetivo não é oferecer suporte ao padrão completo ou a todos os arquivos formatados exóticos (mas compatíveis com o padrão) existentes. Algumas suposições são feitas, como:
Atualmente, segyio suporta:
A funcionalidade de escrita no segyio destina-se principalmente a modificar ou adaptar arquivos. Um arquivo criado do zero não é necessariamente um arquivo SEG-Y de acordo com as especificações, pois apenas escrevemos necessariamente os campos de cabeçalho que o segyio precisa para entender a geometria. Ainda é altamente recomendado que os arquivos SEG-Y sejam mantidos e escritos de acordo com as especificações, mas o segyio não impõe isso.
O Segyio pode lidar com muitos arquivos do tipo SEG-Y, ou seja, o segyio lida com arquivos que não estão estritamente em conformidade com o padrão SEG-Y. Segyio também não discrimina entre as revisões, mas tenta usar as informações disponíveis no arquivo. Para referência de um padrão real , consulte as publicações da SEG:
Aceitamos todos os tipos de contribuições; consulte CONTRIBUTING.md.
xarray
Alan Richardson escreveu uma ótima ferramenta para usar xarray com arquivos segy, que ele demonstra neste caderno
Pequenos arquivos formatados em SEG-Y são incluídos no repositório para fins de teste. Os dados não fazem sentido e são previsíveis, além de serem reproduzíveis usando segyio. O arquivo de testes está localizado no diretório test-data. Para reproduzir o arquivo de dados, construa segyio e execute o programa de teste make-file.py
, make-ps-file.py
e make-rotated-copies.py
como tal:
python examples / make - file . py small . sgy 50 1 6 20 25
python examples / make - ps - file . py small - ps . sgy 10 1 5 1 4 1 3
python examples / make - rotated - copies . py small . sgy
O arquivo small-lsb.sgy foi criado executando o programa flip-endianness. Este programa está incluído na árvore fonte do segyio, mas não faz parte do pacote, e não se destina à distribuição e instalação, apenas à reprodução de arquivos de teste.
Os arquivos unix sísmicos small.su e small-lsb.su foram criados pelos seguintes comandos:
segyread tape=small.sgy ns=50 remap=tracr,cdp byte=189l,193l conv=1 format=1
> small-lsb.su
suswapbytes < small.su > small-lsb.su
Se você possui pequenos arquivos de dados com licença gratuita, fique à vontade para enviá-los para o projeto!
Importe bibliotecas úteis:
import segyio
import numpy as np
from shutil import copyfile
Abra o arquivo segy e inspecione-o:
filename = 'name_of_your_file.sgy'
with segyio . open ( filename ) as segyfile :
# Memory map file for faster reading (especially if file is big...)
segyfile . mmap ()
# Print binary header info
print ( segyfile . bin )
print ( segyfile . bin [ segyio . BinField . Traces ])
# Read headerword inline for trace 10
print ( segyfile . header [ 10 ][ segyio . TraceField . INLINE_3D ])
# Print inline and crossline axis
print ( segyfile . xlines )
print ( segyfile . ilines )
Leia o cubo de dados pós-pilha contido no arquivo segy:
# Read data along first xline
data = segyfile . xline [ segyfile . xlines [ 1 ]]
# Read data along last iline
data = segyfile . iline [ segyfile . ilines [ - 1 ]]
# Read data along 100th time slice
data = segyfile . depth_slice [ 100 ]
# Read data cube
data = segyio . tools . cube ( filename )
Leia o cubo de dados pré-pilha contido no arquivo segy:
filename = 'name_of_your_prestack_file.sgy'
with segyio . open ( filename ) as segyfile :
# Print offsets
print ( segyfile . offset )
# Read data along first iline and offset 100: data [nxl x nt]
data = segyfile . iline [ 0 , 100 ]
# Read data along first iline and all offsets gath: data [noff x nxl x nt]
data = np . asarray ([ np . copy ( x ) for x in segyfile . iline [ 0 : 1 , :]])
# Read data along first 5 ilines and all offsets gath: data [noff nil x nxl x nt]
data = np . asarray ([ np . copy ( x ) for x in segyfile . iline [ 0 : 5 , :]])
# Read data along first xline and all offsets gath: data [noff x nil x nt]
data = np . asarray ([ np . copy ( x ) for x in segyfile . xline [ 0 : 1 , :]])
Ler e compreender dados razoavelmente “não estruturados” (por exemplo, dados classificados em coletas comuns):
filename = 'name_of_your_prestack_file.sgy'
with segyio . open ( filename , ignore_geometry = True ) as segyfile :
segyfile . mmap ()
# Extract header word for all traces
sourceX = segyfile . attributes ( segyio . TraceField . SourceX )[:]
# Scatter plot sources and receivers color-coded on their number
plt . figure ()
sourceY = segyfile . attributes ( segyio . TraceField . SourceY )[:]
nsum = segyfile . attributes ( segyio . TraceField . NSummedTraces )[:]
plt . scatter ( sourceX , sourceY , c = nsum , edgecolor = 'none' )
groupX = segyfile . attributes ( segyio . TraceField . GroupX )[:]
groupY = segyfile . attributes ( segyio . TraceField . GroupY )[:]
nstack = segyfile . attributes ( segyio . TraceField . NStackedTraces )[:]
plt . scatter ( groupX , groupY , c = nstack , edgecolor = 'none' )
Escreva o arquivo segy usando o mesmo cabeçalho de outro arquivo, mas multiplique os dados por *2
input_file = 'name_of_your_input_file.sgy'
output_file = 'name_of_your_output_file.sgy'
copyfile ( input_file , output_file )
with segyio . open ( output_file , "r+" ) as src :
# multiply data by 2
for i in src . ilines :
src . iline [ i ] = 2 * src . iline [ i ]
Crie um arquivo segy a partir do sctrach
filename='name_of_your_file.sgy'
% Inspect segy
Segy_struct=SegySpec(filename,189,193,1);
% Read headerword inline for each trace
Segy.get_header(filename,'Inline3D')
%Read data along first xline
data= Segy.readCrossLine(Segy_struct,Segy_struct.crossline_indexes(1));
%Read cube
data=Segy.get_cube(Segy_struct);
%Write segy, use same header but multiply data by *2
input_file='input_file.sgy';
output_file='output_file.sgy';
copyfile(input_file,output_file)
data = Segy.get_traces(input_file);
data1 = 2*data;
Segy.put_traces(output_file, data1);
Muitas vezes surgem problemas quando alguém tem dificuldade com o desempenho do segyio, principalmente ao criar novos arquivos. O culpado geralmente é este código:
with segyio.create('new.sgy', spec) as dst:
dst.header = headers
O código em si está perfeitamente ok, mas tem um comportamento sutil em alguns sistemas quando o arquivo é criado recentemente: ele está executando muitas gravações dispersas em um arquivo esparso. Isso pode ser rápido ou lento, dependendo muito do sistema de arquivos.
Reescreva o loop para gravar no arquivo de forma contígua:
with segyio.create('new.sgy', spec) as dst:
for i in range(spec.tracecount):
dst.header[i] = headers[i]
dst.trace[i] = traces[i]
Se o arquivo for uma cópia modificada de outro arquivo, sem alterar o comprimento do rastreamento, geralmente é mais rápido (e mais fácil!) Copiar primeiro o arquivo sem segyio e depois usar segyio para modificar a cópia no local:
shutil.copyfile(srcfile, dstfile)
with segyio.open(dstfile) as f:
f.header = headers
Este erro aparece quando o carregador não consegue encontrar a biblioteca principal do segyio. Se você definiu explicitamente o prefixo de instalação (com -DCMAKE_INSTALL_PREFIX
), você deve configurar seu carregador para também procurar neste prefixo, seja com um arquivo ld.conf.d
ou com a variável LD_LIBRARY_PATH
.
Se você não configurou CMAKE_INSTALL_PREFIX
, cmake será instalado por padrão em /usr/local
, que seu carregador geralmente conhece. Em sistemas baseados em Debian, a biblioteca geralmente é instalada em /usr/local/lib
, o que o carregador pode não conhecer. Veja a edição nº 239.
sudo ldconfig
geralmente resolve)-DCMAKE_INSTALL_LIBDIR=lib64
Esta exceção é levantada quando segyio tenta abrir o arquivo em modo estrito, supondo que o arquivo seja um volume 3D regular e classificado. Se o arquivo for apenas uma coleção de rastreamentos em ordem arbitrária, isso falhará.
Verifique se os parâmetros de entrada segyio.open iline
e xline
estão corretos para o arquivo atual. Segyio também suporta arquivos que são apenas uma coleção de rastros, mas é preciso informar que não há problema em fazê-lo. Passe strict = False
ou ignore_geometry = True
para segyio.open
para permitir ou forçar o modo não estruturado, respectivamente. Observe que f.iline
e recursos semelhantes agora estão desativados e gerarão erros.
O Segyio foi inicialmente escrito e é mantido pela Equinor ASA como uma forma gratuita, simples e fácil de usar de interagir com dados sísmicos que podem ser adaptados às nossas necessidades e como uma contribuição para a comunidade de software livre.