Commit 77cef2b1 authored by David Hendriks's avatar David Hendriks
Browse files

made the parse output a bit more functional

parent 64578be9
Loading
Loading
Loading
Loading
+17 −13
Original line number Diff line number Diff line
@@ -122,7 +122,7 @@ def from_binary_c_config(config_file, flag):
    return res


def return_compilation_dict():
def return_compilation_dict(verbose=False):
    """
    Function to build the compile command for the shared library

@@ -206,6 +206,8 @@ def return_compilation_dict():
    ]
    libs = "{} {}".format(" ".join(library_paths), " ".join(non_library_paths))


    if verbose:
        print(
            "Building shared library for custom logging with (binary_c.h) at {} on {}\n".format(
                BINARY_C_SRC_DIR, socket.gethostname()
@@ -220,7 +222,7 @@ def return_compilation_dict():
    return {"cc": cc, "ld": ld, "ccflags": ccflags, "libs": libs, "inc": inc}


def compile_shared_lib(code, sourcefile_name, outfile_name):
def compile_shared_lib(code, sourcefile_name, outfile_name, verbose=False):
    """
    Function to write the custom logging code to a file and then compile it.
    """
@@ -245,9 +247,11 @@ def compile_shared_lib(code, sourcefile_name, outfile_name):
    command = " ".join(command.split())

    # Execute compilation
    if verbose:
        print("Executing following command:\n{command}".format(command=command))
    res = subprocess.check_output("{command}".format(command=command), shell=True)

    if verbose:
        if res:
            print("Output of compilation command:\n{}".format(res))

+25 −13
Original line number Diff line number Diff line
@@ -136,14 +136,18 @@ def run_system_with_log(**kwargs):

def parse_output(output, selected_header):
    """
    Function that parses output of binaryc when it is construction like this:
    DAVID_SINGLE_ANALYSIS t=0 mass=20 
    Function that parses output of binary_c:

    This function works in two cases:
    if the caught line contains output like 'example_header time=12.32 mass=0.94 ..'
    or if the line contains output like 'example_header 12.32 0.94'

    You can give a 'selected_header' to catch any line that starts with that. 
    Then the values will be put into a dictionary.
    TODO: Think about exporting to numpy array or pandas
    
    TODO: Think about exporting to numpy array or pandas instead of a defaultdict
    """

    value_dicts     = []
    val_lists       = []

@@ -155,16 +159,24 @@ def parse_output(output, selected_header):

            # Select parts
            header = split_line[0]
            value_array = split_line[1:]
            values_list = split_line[1:]

            # print(values_list)
            # Catch line starting with selected header
            if header == selected_header:
                # print(value_array)
                # Make a dict
                # Check if the line contains '=' symbols:
                value_dict = {}
                for el in value_array:
                if all('=' in el for el in values_list):
                    for el in values_list:
                        key, val = el.split("=")
                    value_dict[key] = val
                        value_dict[key.strip()] = val.strip()
                    value_dicts.append(value_dict)
                else:
                    if any('=' in el for el in values_list):
                        raise ValueError('Caught line contains some = symbols but not all of them do. aborting run')
                    else:
                        for i, val in enumerate(values_list):
                            value_dict[i] = val
                        value_dicts.append(value_dict)

    if len(value_dicts) == 0:
+21 −7
Original line number Diff line number Diff line
@@ -20,7 +20,6 @@ Use these as inspiration/base.
def run_example_binary():
    """
    Function to run a binary system. Very basic approach which directly adresses the run_binary(..) python-c wrapper function. 

    """

    m1 = 15.0  # Msun
@@ -46,7 +45,6 @@ def run_example_binary():
    output = binary_c.run_binary(argstring)
    print(output)


# run_example_binary()


@@ -60,6 +58,8 @@ def run_example_binary_with_run_system():
    run_system: mostly just makes passing arguments to the function easier. It also loads all the necessary defaults in the background
    parse_output: Takes the raw output of binary_c and selects those lines that start with the given header. 
    Note, if you dont use the custom_logging functionality binary_c should be configured to have output that starts with that given header

    The parsing of the output only works correctly if either all of the values are described inline like `mass=<number>' or none of them are.    
    """

    import pandas as pd
@@ -68,16 +68,31 @@ def run_example_binary_with_run_system():
    # Run system. all arguments can be given as optional arguments.
    output = run_system(M_1=10, M_2=20, separation=0, orbital_period=100000000000)

    # print(output)

    # Catch results that start with a given header. (Mind that binary_c has to be configured to print them if your not using a custom logging function)
    result_example_header = parse_output(output, "example_header")
    result_example_header_1 = parse_output(output, selected_header="example_header_1")
    result_example_header_2 = parse_output(output, selected_header="example_header_2")

    # print(result_example_header_1)

    #### Now do whatever you want with it:
    # Put it in numpy arrays
    # t_res = np.asarray(result_example_header['t'], dtype=np.float64, order='C')
    # m_res = np.asarray(result_example_header['mass'], dtype=np.float64, order='C')

    # Or put them into a pandas array


    # Cast the data into a dataframe.
    df = pd.DataFrame.from_dict(result_example_header, dtype=np.float64)
    # This example automatically catches the column names because the binary_c output line is constructed as 'example_header_1 time=<number>..'
    df = pd.DataFrame.from_dict(result_example_header_1, dtype=np.float64)
    print(df)

    # This example has column headers which are numbered, but we can override that with custom headers.
    df2 = pd.DataFrame.from_dict(result_example_header_2, dtype=np.float64)
    df2.columns=['time', 'mass_1', 'mass_2', 'st1', 'st2', 'sep', 'ecc']
    print(df2)

    # print(df)
    # sliced_df = df[df.t < 1000] # Cut off late parts of evolution
@@ -85,8 +100,7 @@ def run_example_binary_with_run_system():

    # Some routine to plot.

# run_example_binary_with_run_system()

run_example_binary_with_run_system()

def run_example_binary_with_custom_logging():
    """
+30 −29
Original line number Diff line number Diff line
# from distutils.core import setup, Extension
from distutils.core import setup, Extension
# from setuptools import find_packages
from setuptools import setup, find_packages, Extension
# from setuptools import setup, find_packages, Extension
import os
import subprocess
import re
@@ -57,22 +57,7 @@ API_h = os.environ["BINARY_C"] + "/src/API/binary_c_API.h"
binary_c_define_macros.extend([("BINARY_C_API_H", API_h)])


def readme():
    with open('README.md') as f:
        return f.read()


setup(
    name="binary_c",
    version="1.0",
    description="This is a python API for binary_c by Rob Izzard and collaborators",
    author="Jeff Andrews and Robert Izzard and David Hendriks",
    author_email="andrews@physics.uoc.gr and r.izzard@surrey.ac.uk and rob.izzard@gmail.com and davidhendriks93@gmail.com",
    long_description=readme(),
    url="https://gitlab.eps.surrey.ac.uk/ri0005/binary_c-python",
    license="",
    ext_modules=[
        Extension(
binary_c_python_api_module = Extension(
    "binary_c",
    ["src/binary_c_python.c"],
    include_dirs=[
@@ -98,5 +83,21 @@ setup(
    extra_objects=[],
    extra_compile_args=[],
)

def readme():
    with open('README.md') as f:
        return f.read()

setup(
    name="binary_c",
    version="1.0",
    description="This is a python API for binary_c by Rob Izzard and collaborators",
    author="Jeff Andrews and Robert Izzard and David Hendriks",
    author_email="andrews@physics.uoc.gr and r.izzard@surrey.ac.uk and rob.izzard@gmail.com and davidhendriks93@gmail.com",
    long_description=readme(),
    url="https://gitlab.eps.surrey.ac.uk/ri0005/binary_c-python",
    license="",
    ext_modules=[
        binary_c_python_api_module
    ],  # binary_c must be loaded
)