Extending flitsr advanced types¶
flitsr provides a number of techniques implemented as advanced types,
which you can employ when using flitsr. However flitsr also provides the
functionality for you to easily create your own advanced type, if you would like
to extend flitsr to support another technique.
To create a new technique for an advanced type, you will need to define a class
which extends a current advanced type base class. The available advanced types
are given in flitsr advanced types. You would create your advanced type either within
the advanced package of flitsr, or (more likely) create a separate
plugin. Creating this concrete implementation of an
advanced type using either of these two ways will allow flitsr to
automatically discover and make available your advanced type.
To create an advanced type plugin, use the
flitsr.advanced entry point, for example:
[project.entry-points.'flitsr.advanced']
adv_mthd = "my-package.custom_adv_type:CustomTechnique"
Where CustomTechnique is a custom advanced type that inherits one of the
advanced types.
Since custom techniques will have various different algorithms and potentially
other input, flitsr makes it easy to customize advanced types by providing some helpful structure and functions for advanced
types.
Passing input parameters – the __init__ method¶
flitsr allows any advanced type to take additional inputs which they can use
within their implementation. To do this, flitsr analyzes the signature of
the __init__ method of any advanced type, and processes the parameters of
this method, making them automatically available as command line parameters,
which flitsr will provide when calling the advanced type.
As an example, let’s use the parallel advanced type. The __init__ method
of the parallel advanced type is as follows:
def __init__(self, parType: str = 'msp'):
self.parType = parType
This advanced type takes one additional parameter, parType which has a type
hint indicating it is a str. It also has a default value set, which is
'msp'.
flitsr automatically processes this advanced types __init__ method, and
extracts this information, automatically producing the command line option
–parallel-parType. The command line option is
automatically created to have a parameter with type str, which has the
default value of 'msp'.
flitsr uses argparse
for its command line processing, which will automatically support conversion to
any primitive type. For conversion to a non-primitive type, you must implement a
method named _<param> in your advanced type class, where <param> is the
name of the __init__ parameter to convert, which takes a string and converts
it to your custom type. For example, if your technique takes a parameter my_date,
which is a date in the format 'Jun 1 2005 1:33PM', you could specify the
function:
@staticmethod
def _my_date(date_str : str):
from datetime import datetime
return datetime.strptime(date_str, '%b %d %Y %I:%M%p').date()
This would be automatically discovered by flitsr, and will be passed to
argparse to be used to convert the parameter to a date object.
Advanced type attributes – existing¶
In some cases, you would like to define a parameter to your function that takes
the value of an argument already passed to flitsr, instead of defining a new
command line argument. For example, you might want your technique to use the
--tiebrk argument to flitsr, with which the user specifies how to break
ties throughout flitsr. To include already defined arguments in the
parameters of your advanced type, flitsr provides the existing decorator function which can be applied to
the __init__ method. The decorator has the following usage:
- flitsr.advanced.attributes.existing(*params: str)¶
A python decorator to mark the given parameter(s) as one(s) already defined in FLITSR’s arguments. These parameters for the decorated advanced type are therefore not added as FLITSR command line arguments, but are instead taken from the existing command line arguments.
- Parameters:
*params – str: The parameters of the __init__ function to mark as already existing
flitsrparameters.
Using the example of the --tiebrk option, you would do the following:
@existing('tiebrk')
def __init__(self, tiebrk: Tiebrk):
self.tiebrk = tiebrk
flitsr would then automatically fill that parameter with the value of the
--tiebrk command line argument when instantiating your advanced type.
Advanced type attributes – choices¶
For some parameters, you may also want to specify a number of pre-defined
choices for a particular parameter. flitsr allows you to do this using the
choices decorator, which can be applied
to the __init__ method, similar to the existing decorator. The choices decorator has the following usage:
- flitsr.advanced.attributes.choices(param: str, choices: Collection[Any])¶
An advanced types decorator to specfiy the choices available for a given parameter. The given choices will be added as available choices for the command line argument for FLITSR.
- Parameters:
param – str: The parameter to set choices for.
choices – Collection[Any]: The collection of choices for the parameter.
As an example, the parType parameter of our --parallel example has four
pre-defined strings that it accepts: bdm, msp, hwk, and vwk. To
define this set of choices for the parallel advanced type, we would do the
following:
@choices('parType', ['bdm', 'msp', 'hwk', 'vwk'])
def __init__(self, parType: str = 'msp'):
self.parType = parType
This is the implementation used for the __init__ method of the parallel
technique, from which flitsr automatically creates the
–parallel-parType command line option.
Advanced type attributes – print_name¶
The last type of helper method that flitsr provides is the print_name decorator. This is a class level
decorator, that can be used on an advanced type class to define a different name
to be used when flitsr prints results to output files. This name will then
appear in file names and merged result files. The usage of this
decorator is as follows:
- flitsr.advanced.attributes.print_name(print_name: str)¶
An advanced types decorator to specfiy an alternative name for the decorated class to use when printing results to a file. By default the lower-case name of the advanced type is used.
- Parameters:
print_name – str: The name to use when printing this advanced type.
An example of the usage is for the sbfl advanced type in flitsr. For
this advanced type, we would like a different name to be used when printing out
results, namely 'base' instead of 'sbfl'. The sbfl class is thus
defined as:
@print_name('base')
class SBFL(Ranker):
...