:- ensure_loaded( library(csv) ). % :- lib( stoics_lib:en_list/2 ). /** mtx_read_table( +CsvF, +RowsName, -Table, +OptS ). Reads a table in from a file (CsvF). A table is a delimited file in which the first row is one short than the rest.
RowsName is added as the first argument in the read-in Table's first row. OptS * match(Match=true) whether to match_arity(Match) rows read in (see csv//2 options). * sep(Sep=_) the mtx/2 version of separator(Sep) option of csv//2 (mtx_sep/2). Defaults to csv//2 version which is based on filename extension. Any other OptS are passed to csv//2.
As per mtx/3 convention OptS can be a single option (un-listed) or a list of options. == ?- tmp_file( testo, TmpF ), csv_write_file( TmpF, [row(c_a,c_b),row(1,a,b),row(2,aa,bb)], [match_arity(false),separator(0'\t)] ), mtx_read_table( TmpF, samples, Tbl, sep(tab) ). TmpF = '/tmp/pl_testo_12445_0', Tbl = [row(samples, c_a, c_b), row(1, a, b), row(2, aa, bb)]. == @author nicos angelopoulos @version 0.1 2018/2/3 @see mtx_sep/2, csv//2 */ mtx_read_table( File, RowsName, Table, OptionS ) :- en_list( OptionS, Options ), ( select_option(sep(MtxSep),Options,Options0) -> mtx_sep( MtxSep, CsvSep ), Options1 = [separator(CsvSep)|Options0] ; csv:default_separator( File, Options, Options1 ) ), select_option( match(MatchPrv), Options1, Options2, _ ), ( var(MatchPrv) -> Match = true; Match = MatchPrv ), csv:make_csv_options([match_arity(Match)|Options2], RecOptionsPrv, Options3), setup_call_cleanup( open(File, read, Stream, Options3), ( csv_read_row(Stream, Row0, RecOptionsPrv), ( Match == true -> % fixme: this hacking: RecOptionsPrv = csv_options(CopA,CopB,CopC,CopD,CopE,CopF,HdrAri,CopH,CopI), RowsAri is HdrAri + 1, RecOptions = csv_options(CopA,CopB,CopC,CopD,CopE,CopF,RowsAri,CopH,CopI) ; RecOptionsPrv = RecOptions ), functor( Row0, _, HdrArity ), Arity is HdrArity + 1, Row0 =.. [Row0Nm|Row0Args], Hdr =.. [Row0Nm,RowsName|Row0Args], mtx_read_table_stream_rows(Hdr, Stream, Match, Arity, Table, RecOptions) ), close(Stream)). mtx_read_table_stream_rows( end_of_file, _Stream, _Match, _Arity, Rows, _Opts ) :- !, Rows = []. mtx_read_table_stream_rows(Row, Stream, Match, Arity, [Row|Rows], Opts ) :- mtx_read_table_row_match_arity( Match, Arity, Row ), csv_read_row( Stream, NxtRow, Opts ), mtx_read_table_stream_rows(NxtRow, Stream, Match, Arity, Rows, Opts ). mtx_read_table_row_match_arity( false, _Arity, _Row ). mtx_read_table_row_match_arity( true, Arity, Row ) :- functor( Row, _, Rarity ), ( Rarity =:= Arity -> true; throw(arity_mismatch(Arity,Rarity,Row)) ).