Fsdb::IO(3)
π Fsdb::IO(3) π
okay so this is the Fsdb::IO(3) page from User Contributed Perl Documentation, and bestie, itβs giving base-class main character energy β like it literally says itβs the base class for Fsdb IO, aka FsdbReader and FsdbWriter π«Άβ¨
πΈ NAME πΈ
Fsdb::IO - base class for Fsdb IO (FsdbReader and FsdbWriter). periodt. π
β¨ EXAMPLES β¨
There are several ways to do IO, and we look at several that compute the product of x and y for this input:
#fsdb x y product
1 10 -
2 20 -
The following routes go from most easy-to-use to least, and also from least efficient to most. For IO-intensive work, if fastpath takes 1 unit of time, then using hashes or arrays takes approximately 2 units of time, and thatβs all due to CPU overhead. no cap. π§
π Using A Hash π
The hash route is lowkey the coziest:
use Fsdb::IO::Reader;
use Fsdb::IO::Writer;
# preamble
my $out;
my $in = new Fsdb::IO::Reader(-file => '-', -comment_handler => \$out)
or die "cannot open stdin as fsdb\n";
$out = new Fsdb::IO::Writer(-file => '-', -clone => $in)
or die "cannot open stdin as fsdb\n";
# core starts here
my %hrow;
while ($in->read_row_to_href(\%hrow)) {
$hrow{product} = $hrow{x} * $hrow{y};
$out->write_row_from_href(\%hrow);
};
It can be convenient to use a hash because one can easily extract fields using hash keys, but ngl, hashes can be slow. π’π
π¦ Arrays Instead of Hashes π¦
We can add a bit to the end of the preamble:
my $x_i = $in->col_to_i('x') // die "no x column.\n";
my $y_i = $in->col_to_i('y') // die "no y column.\n";
my $product_i = $in->col_to_i('product') // die "no product column.\n";
And then replace the core with arrays:
my @arow;
while ($in->read_row_to_aref(\@arow)) {
$arow[$product_i] = $arow[$x_i] * $arow[$y_i];
$out->write_row_from_aref(\@arow);
};
This code has two advantages over hrefs: First, there is explicit error checking for presence of the expected fields. Second, arrays are likely a bit faster than hashes. slay. π₯
π§ Objects Instead of Arrays π§
Keeping the same preamble as for arrays, we can directly get internal Fsdb βrow objectsβ with a new core:
# core
my $rowobj;
while ($rowobj = $in->read_rowobj) {
if (!ref($rowobj)) {
# comment
&{$in->{_comment_sub}}($rowobj);
next;
};
$rowobj->[$product_i] = $rowobj->[$x_i] * $rowobj->[$y_i];
$out->write_rowobj($rowobj);
};
This code is a bit faster because we just return the internal representation (a rowobj), rather than copy into an array. β¨
However, unfortunately it doesn't handle comment processing. π
π Fastpathing π
To go really fast, we can build a custom thunk (a chunk of code) that does exactly what we want. This approach is called a βfastpathβ. π
It requires a bit more in the preamble (building on the array version):
my $in_fastpath_sub = $in->fastpath_sub();
my $out_fastpath_sub = $out->fastpath_sub();
And it allows a shorter core (modeled on rowobjs), since the fastpath includes comment processing:
my $rowobj;
while ($rowobj = &$in_fastpath_sub) {
$rowobj->[$product_i] = $rowobj->[$x_i] * $rowobj->[$y_i];
&$out_fastpath_sub($rowobj);
};
This code is the fastest way to implement this block without evaling code. periodt. ππ
FUNCTIONS β¨
okay so this is the function roster, bestie β every method, every internal, every tiny caveat. no skipping. π
new π
$fsdb = new Fsdb::IO;
Creates a new IO object. Usually you should not create a FsdbIO object directly, but instead create a FsdbReader or FsdbWriter β main character move.
Options:
-fh FILE_HANDLEβ write IO to the given file handle.-header HEADER_LINEβ force the header to the givenHEADER_LINE(should be verbatim, including#hor whatever).=backπ (yes, that=backis literally hanging out in the source).-fscode CODEβ define just the column (or field) separatorfscodepart of the header. Seedbfilealterfor a list of valid field separators.-rscode CODEβ define just the row separator part of the header. Seedbfilealterfor a list of valid row separators.-cols CODEβ define just the columns of the header.-compression CODEβ define the compression mode for the file that will take effect after the header.-clone $fsdbβ copy the streamβs configuration from$FSDB, anotherFsdb::IOobject.
_reset_cols π§
$fsdb->_reset_cols
Internal: zero all the mappings in the curren schema. (source spelling, we love a tiny typo π«Ά)
_find_filename_decompressor π
returns the name of the decompression program for FILE if it ends in a compression extension.
config_one π
$fsdb->config_one($arglist_aref);
Parse the first configuration option on the list, removing it.
Options are listed in new.
config βοΈ
$fsdb->config(-arg1 => $value1, -arg2 => $value2);
Parse all options in the list.
default_binmode π
$fsdb->default_binmode();
Set the file to the correct binmode, either given by -encoding at setup, or defaulting from LC_CTYPE or LANG.
If the file is compressed, we will reset binmode after reading the header.
compare π
$result = $fsdb->compare($other_fsdb)
Compares two Fsdb::IO objects, returning the strings "identical" (same field separator, columns, and column order), or maybe "compatible" (same field separator but different columns), or undef if they differ.
close π
$fsdb->close;
Closes the file, frees open file handle, or sends an EOF signal (and undef) down the open queue.
error π¨
$fsdb->error;
Returns a descriptive string if there is an error, or undef if not.
The string will never end in a newline or punctuation.
update_v1_headerrow π§±
internal: create the header the internal schema
parse_v1_headerrow π§
internal: interpet the header
update_headerrow π§±β¨
internal: create the header the internal schema
parse_headerrow π§ β¨
internal: interpet the v2 header. Format is:
#fsdb [-F x] [-R x] [-Z x] columns
All options must come first, start with dashes, and have an argument. (More regular than the v1 header.)
Columns have optional :t type specifiers.
parse_v1_fscode π§©
internal
parse_fscode π§©β¨
Parse the field separator. See dbfilealter for a list of valid values.
parse_rscode π§©π
Internal: Interpret rscodes.
See dbfilealter for a list of valid values.
parse_compression ποΈ
Internal: Interpret compression.
See dbfilealter for a list of valid values.
establish_new_col_mapping πΊοΈ
internal
col_create β
$fsdb->col_create($col_name)
Add a new column named $COL_NAME to the schema. Returns undef on failure, or 1 if sucessful. (Note: does not return the column index on creation because so that "or" can be used for error checking, given that the column number could be zero.) Also, update the header row to reflect this column (compare to "_internal_col_create").
colspec_to_name_type_spec π·οΈ
($name, $type, $type_speced) = $fsdb->colspec_to_name_type($colspec)
Split a colspec into a name, type, and the type as specified (which may be null if no type was given).
_internal_col_create π οΈ
$fsdb->_internal_col_create($colspec)
For internal "Fsdb::IO" use only. Create a new column $COL_NAME, just like "col_create", but do not update the header row (as that function does).
field_contains_fs π΅οΈββοΈ
$boolean = $fsdb->field_contains_fs($field);
Determine if the $FIELD contains $FSDBβs fscode (in which case it is malformed).
fref_contains_fs π΅οΈββοΈβ¨
$boolean = $fsdb->fref_contains_fs($fref);
Determine if any field in $FREF contains $FSDBβs fscode (in which case it is malformed).
correct_fref_containing_fs π©Ή
$boolean = $fsdb->correct_fref_containing_fs($fref);
Patch up any field in $FREF contains $FSDBβs fscode, as best as possible, but turning the field separator into underscores. Updates $FREF in place, and returns if it was altered. This function looses data.
β οΈ bestie, this one looses data β the source said it, and the source meant it. π
fscode π€
$fscode = $fsdb->fscode;
Returns the fscode of the given database. (The encoded verison representing the field separator.) See also fs to get the actual field separator.
fs π‘
$fscode = $fsdb->fs;
Returns the field separator. See "fscode" to get the "encoded" version.
rscode π§΅
$rscode = $fsdb->rscode;
Returns the rscode of the given database.
ncols π’
@fields = $fsdb->ncols;
Return the number of columns.
cols π
$fields_aref = $fsdb->cols;
Returns the column names (the field names, without type specifications) of the open database as an aref.
colspecs πβ¨
$fields_aref = $fsdb->colspecs();
Returns the column headings (the field names) of the open database as an aref.
col_to_i π―
$coli = $fsdb->col_to_i($column_name);
Returns the column index (0-based) of a given $COLUMN_NAME. (Names cannot have types with them.)
Note: tests for existence of columns must use "defined", since the index can be 0 which would be interpreted as false.
colspec_to_i π―β¨
$coli = $fsdb->colspec_to_i($column_specification);
Returns the column index (0-based) of a given $COLUMN_NAME. Name may or may not include a type.
Note: tests for existence of columns must use "defined", since the index can be 0 which would be interpreted as false.
col_to_name π·οΈβ¨
@fields = $fsdb->col_to_name($column_name);
Returns the column anme a given $COLUMN_NAME_OR_INDEX. (source says anme, and we respect the typo π«Ά)
col_to_type π
@fields = $fsdb->col_to_type($column_name, $force_type);
Returns the column type (and undef if type is not required, unless $FORCE_TYPE) of a given $COLUMN_NAME.
col_to_colspec π§Ύ
@fields = $fsdb->col_to_colspec($column_name, $force_type);
Returns the column specification (type is optional, unless $FORCE_TYPE) of a given $COLUMN_NAME.
col_type_is_numeric π’β¨
@fields = $fsdb->col_type_is_numeric($column_name);
Returns non-zero if column specification is numeric. (Actually, returns 1 for integers and 2 for floats.)
i_to_col π―π
@fields = $fsdb->i_to_col($column_index);
Return the name of the COLUMN_INDEX-th (0-based) column.
fastpath_cancel ποΈπ¨
$fsdb->fastpath_cancel();
Discard any active fastpath code and allow fastpath-incompatible operations.
codify π§¬
($code, $has_last_refs) = $self->codify($underscored_pseudocode);
Convert db-code $UNDERSCORED_PSEUDOCODE into perl code in the context of a given Fsdb stream.
We return a string of code $CODE that refs "@{$fref}" and "@{$lfref}" for the current and prior row arrays, and a flag $HAS_LAST_REFS if "@{$lfref}" is needed. It is the callers job to set these up, probably by evaling the returned string in the context of those variables.n π (that trailing n is in the source, bestie)
The conversion is a rename of all _foo's into database fields. For more perverse needs, _foo(N) means the Nth field after _foo. Also, as of 29-Jan-00, _last_foo gives the last row's value (_last_foo(N) is not supported). To convert we eval $codify_code.
20-Feb-07: _FROMFILE_foo opens the file called _foo and includes it in place.
NEEDSWORK: Should make some attempt to catch misspellings of column names.
clean_potential_columns π§Ό
@clean = Fsdb::IO::clean_potential_columns(@dirty);
Clean up user-provided column names.
tiny sign-off: this page is serving perl v5.32.1 source/version energy, dated 2024-08-02. thatβs the footer, but make it cute. πβ¨π
π¦ where this page comes from
- epel 9: perl-Fsdb 2:3.9-1.el9 Β· GPLv2
- π girlified by deepseek-ai/DeepSeek-V4.1-Flash-1017 on : a language model's rewrite of the original, under its terms