#9620 Add reader for pressure depth text file.

This commit is contained in:
Kristian Bendiksen 2023-01-11 16:36:37 +01:00
parent 061e0d4688
commit 10187a934c
9 changed files with 391 additions and 0 deletions

View File

@ -75,6 +75,7 @@ set(SOURCE_GROUP_HEADER_FILES
${CMAKE_CURRENT_LIST_DIR}/RifProjectSummaryDataWriter.h
${CMAKE_CURRENT_LIST_DIR}/RifReaderOpmRft.h
${CMAKE_CURRENT_LIST_DIR}/RifRftSegment.h
${CMAKE_CURRENT_LIST_DIR}/RifPressureDepthTextFileReader.h
)
set(SOURCE_GROUP_SOURCE_FILES
@ -151,6 +152,7 @@ set(SOURCE_GROUP_SOURCE_FILES
${CMAKE_CURRENT_LIST_DIR}/RifProjectSummaryDataWriter.cpp
${CMAKE_CURRENT_LIST_DIR}/RifReaderOpmRft.cpp
${CMAKE_CURRENT_LIST_DIR}/RifRftSegment.cpp
${CMAKE_CURRENT_LIST_DIR}/RifPressureDepthTextFileReader.cpp
)
list(APPEND CODE_HEADER_FILES ${SOURCE_GROUP_HEADER_FILES})

View File

@ -0,0 +1,137 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2023 - Equinor ASA
//
// ResInsight is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// ResInsight is distributed in the hope that it will be useful, but WITHOUT ANY
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE.
//
// See the GNU General Public License at <http://www.gnu.org/licenses/gpl.html>
// for more details.
//
/////////////////////////////////////////////////////////////////////////////////
#include "RifPressureDepthTextFileReader.h"
#include "RiaDefines.h"
#include "RigPressureDepthData.h"
#include "RifFileParseTools.h"
#include "cafAssert.h"
#include <QFile>
#include <QTextStream>
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
std::pair<std::vector<RigPressureDepthData>, QString> RifPressureDepthTextFileReader::readFile( const QString& filePath )
{
std::vector<RigPressureDepthData> items;
QFile file( filePath );
if ( !file.open( QIODevice::ReadOnly | QIODevice::Text ) )
{
return std::make_pair( items, QString( "Unable to open file: %1" ).arg( filePath ) );
}
QString separator = " ";
QTextStream in( &file );
while ( !in.atEnd() )
{
QString line = in.readLine();
if ( isHeaderLine( line ) )
{
QStringList headerValues = RifFileParseTools::splitLineAndTrim( line, separator );
RigPressureDepthData data;
data.setWellName( headerValues[1] );
items.push_back( data );
}
else if ( isDateLine( line ) )
{
// TODO: parse date
}
else if ( isPropertiesLine( line ) || isUnitsLine( line ) || isCommentLine( line ) )
{
// Ignored.
}
else if ( std::optional<std::pair<double, double>> p = parseDataLine( line ) )
{
auto [pressure, depth] = p.value();
items.back().addPressureAtDepth( pressure, depth );
}
}
return std::make_pair( items, "" );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RifPressureDepthTextFileReader::isHeaderLine( const QString& line )
{
return line.startsWith( "WELLNAME" );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RifPressureDepthTextFileReader::isCommentLine( const QString& line )
{
return line.startsWith( "--" );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RifPressureDepthTextFileReader::isDateLine( const QString& line )
{
return line.startsWith( "DATE" );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RifPressureDepthTextFileReader::isPropertiesLine( const QString& line )
{
// TODO: this might be to strict..
return line.startsWith( "PRESSURE DEPTH" );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RifPressureDepthTextFileReader::isUnitsLine( const QString& line )
{
// TODO: this might be to strict..
return line.startsWith( "BARSA METRES" );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
std::optional<std::pair<double, double>> RifPressureDepthTextFileReader::parseDataLine( const QString& line )
{
// Expect two data values separated by one space
QStringList values = RifFileParseTools::splitLineAndTrim( line, " " );
if ( values.size() != 2 ) return {};
// First value is pressure
bool isOk = false;
double pressure = values[0].toDouble( &isOk );
if ( !isOk ) return {};
// Second value is depth
double depth = values[1].toDouble( &isOk );
if ( !isOk ) return {};
return std::make_pair( pressure, depth );
}

View File

@ -0,0 +1,45 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2023 - Equinor ASA
//
// ResInsight is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// ResInsight is distributed in the hope that it will be useful, but WITHOUT ANY
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE.
//
// See the GNU General Public License at <http://www.gnu.org/licenses/gpl.html>
// for more details.
//
/////////////////////////////////////////////////////////////////////////////////
#pragma once
#include <QString>
#include <memory>
#include <optional>
#include <vector>
class RigPressureDepthData;
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
class RifPressureDepthTextFileReader
{
public:
static std::pair<std::vector<RigPressureDepthData>, QString> readFile( const QString& fileName );
private:
static bool isHeaderLine( const QString& line );
static bool isCommentLine( const QString& line );
static bool isDateLine( const QString& line );
static bool isPropertiesLine( const QString& line );
static bool isUnitsLine( const QString& line );
static std::optional<std::pair<double, double>> parseDataLine( const QString& line );
};

View File

@ -95,6 +95,7 @@ set(SOURCE_GROUP_HEADER_FILES
${CMAKE_CURRENT_LIST_DIR}/RigSurfaceResampler.h
${CMAKE_CURRENT_LIST_DIR}/RigSurfaceStatisticsCalculator.h
${CMAKE_CURRENT_LIST_DIR}/RigWellLogIndexDepthOffset.h
${CMAKE_CURRENT_LIST_DIR}/RigPressureDepthData.h
)
set(SOURCE_GROUP_SOURCE_FILES
@ -187,6 +188,7 @@ set(SOURCE_GROUP_SOURCE_FILES
${CMAKE_CURRENT_LIST_DIR}/RigSurfaceResampler.cpp
${CMAKE_CURRENT_LIST_DIR}/RigSurfaceStatisticsCalculator.cpp
${CMAKE_CURRENT_LIST_DIR}/RigWellLogIndexDepthOffset.cpp
${CMAKE_CURRENT_LIST_DIR}/RigPressureDepthData.cpp
)
list(APPEND CODE_HEADER_FILES ${SOURCE_GROUP_HEADER_FILES})

View File

@ -0,0 +1,65 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2023 - Equinor ASA
//
// ResInsight is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// ResInsight is distributed in the hope that it will be useful, but WITHOUT ANY
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE.
//
// See the GNU General Public License at <http://www.gnu.org/licenses/gpl.html>
// for more details.
//
/////////////////////////////////////////////////////////////////////////////////
#include "RigPressureDepthData.h"
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RigPressureDepthData::RigPressureDepthData()
{
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RigPressureDepthData::~RigPressureDepthData()
{
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RigPressureDepthData::setWellName( const QString& wellName )
{
m_wellName = wellName;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
QString RigPressureDepthData::wellName() const
{
return m_wellName;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RigPressureDepthData::addPressureAtDepth( double pressure, double depth )
{
m_values.push_back( std::make_pair( pressure, depth ) );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
std::vector<std::pair<double, double>> RigPressureDepthData::getPressureDepthValues() const
{
return m_values;
}

View File

@ -0,0 +1,45 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2023 - Equinor ASA
//
// ResInsight is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// ResInsight is distributed in the hope that it will be useful, but WITHOUT ANY
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE.
//
// See the GNU General Public License at <http://www.gnu.org/licenses/gpl.html>
// for more details.
//
/////////////////////////////////////////////////////////////////////////////////
#pragma once
#include "RiaDefines.h"
#include <QString>
#include <vector>
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
class RigPressureDepthData
{
public:
RigPressureDepthData();
~RigPressureDepthData();
void setWellName( const QString& name );
QString wellName() const;
void addPressureAtDepth( double pressure, double depth );
std::vector<std::pair<double, double>> getPressureDepthValues() const;
private:
QString m_wellName;
std::vector<std::pair<double, double>> m_values;
};

View File

@ -85,6 +85,7 @@ set(SOURCE_GROUP_SOURCE_FILES
${CMAKE_CURRENT_LIST_DIR}/RifEclipseTextFileReader-Test.cpp
${CMAKE_CURRENT_LIST_DIR}/RiaSummaryStringTools-Test.cpp
${CMAKE_CURRENT_LIST_DIR}/RiaVariableMapper-Test.cpp
${CMAKE_CURRENT_LIST_DIR}/RifPressureDepthTextFileReader-Test.cpp
)
if(RESINSIGHT_ENABLE_GRPC)

View File

@ -0,0 +1,62 @@
#include "gtest/gtest.h"
#include "RiaTestDataDirectory.h"
#include "RifPressureDepthTextFileReader.h"
#include "RigPressureDepthData.h"
#include <QFile>
#include <QTextStream>
static const QString CASE_REAL_TEST_DATA_DIRECTORY_04 =
QString( "%1/RifPressureDepthTextFileReader/" ).arg( TEST_DATA_DIR );
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
TEST( RifPressureDepthTextFileReaderTest, LoadFile )
{
QString fileName = CASE_REAL_TEST_DATA_DIRECTORY_04 + "example_file.txt";
auto [items, errorMessage] = RifPressureDepthTextFileReader::readFile( fileName );
EXPECT_TRUE( errorMessage.isEmpty() );
ASSERT_EQ( 3u, items.size() );
EXPECT_EQ( "'G-14'", items[0].wellName().toStdString() );
std::vector<std::pair<double, double>> values0 = items[0].getPressureDepthValues();
EXPECT_EQ( 4u, values0.size() );
double delta = 0.001;
EXPECT_NEAR( 418.88, values0[0].first, delta );
EXPECT_NEAR( 2726.91, values0[0].second, delta );
EXPECT_EQ( "'G-14'", items[1].wellName().toStdString() );
EXPECT_EQ( 28, items[1].timeStep().date().day() );
EXPECT_EQ( 12, items[1].timeStep().date().month() );
EXPECT_EQ( 1996, items[1].timeStep().date().year() );
std::vector<std::pair<double, double>> values1 = items[1].getPressureDepthValues();
EXPECT_NEAR( 418.88, values1[0].first, delta );
EXPECT_NEAR( 2726.91, values1[0].second, delta );
EXPECT_EQ( "'F-56'", items[2].wellName().toStdString() );
EXPECT_EQ( 15, items[2].timeStep().date().day() );
EXPECT_EQ( 1, items[2].timeStep().date().month() );
EXPECT_EQ( 2012, items[2].timeStep().date().year() );
std::vector<std::pair<double, double>> values2 = items[2].getPressureDepthValues();
EXPECT_EQ( 7u, values2.size() );
EXPECT_NEAR( 413.32, values2[6].first, delta );
EXPECT_NEAR( 2896.555, values2[6].second, delta );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
TEST( RifPressureDepthTextFileReaderTest, LoadFileNonExistingFiles )
{
QString fileName = CASE_REAL_TEST_DATA_DIRECTORY_04 + "this_file_does_not_exist.csv";
auto [items, errorMessage] = RifPressureDepthTextFileReader::readFile( fileName );
EXPECT_FALSE( errorMessage.isEmpty() );
EXPECT_EQ( 0u, items.size() );
}

View File

@ -0,0 +1,32 @@
--TVDMSL
RFT
--
WELLNAME 'G-14'
DATE 28-DEC-1995
PRESSURE DEPTH
BARSA METRES
418.88 2726.91
419.02 2729.36
419.11 2733.29
419.17 2735.26
--
WELLNAME 'G-14'
DATE 28-DEC-1996
PRESSURE DEPTH
BARSA METRES
418.88 2726.91
419.02 2729.36
419.11 2733.29
419.17 2735.26
--
WELLNAME 'F-56'
DATE 15-jan-12
PRESSURE DEPTH
BARSA METRES
414.40 2911.029
415.92 2929.496
417.23 2935.801
415.76 2934.981
414.75 2919.446
413.53 2903.147
413.32 2896.555