An argparse extension for hpman
python3 -m pip install hpargparse
The following example lies in examples/02-brief.
main.py
#!/usr/bin/env python3
from hpman.m import _
import hpargparse
import argparse
def func():
weight_decay = _("weight_decay", 1e-5)
print("weight decay is {}".format(weight_decay))
def main():
parser = argparse.ArgumentParser()
_.parse_file(__file__)
hpargparse.bind(parser, _)
parser.parse_args()
func()
if __name__ == "__main__":
main()
results in:
$ ./main.py
weight decay is 1e-05
$ ./main.py --weight-decay 1e-4
weight decay is 0.0001
$ ./main.py --weight-decay 1e-4 --hp-list
weight_decay: 0.0001
$ ./main.py --weight-decay 1e-4 --hp-list detail
All hyperparameters:
['weight_decay']
Details
ββββββββββββββββ¦ββββββββ¦βββββββββ¦ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β name β type β value β details β
β βββββββββββββββ¬ββββββββ¬βββββββββ¬ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ£
β weight_decay β float β 0.0001 β occurrence[0]: β
β β β β ./main.py:10 β
β β β β 5: β
β β β β 6: import argparse β
β β β β 7: β
β β β β 8: β
β β β β 9: def func(): β
β β β β ==> 10: weight_decay = _("weight_decay", 1e-5) β
β β β β 11: print("weight decay is {}".format(weight_decay)) β
β β β β 12: β
β β β β 13: β
β β β β 14: def main(): β
β β β β 15: parser = argparse.ArgumentParser() β
ββββββββββββββββ©ββββββββ©βββββββββ©ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
$ ./main.py -h
usage: main.py [-h] [--weight-decay WEIGHT_DECAY] [--hp-save HP_SAVE]
[--hp-load HP_LOAD] [--hp-list [{detail,yaml,json}]]
[--hp-detail] [--hp-serial-format {auto,yaml,pickle}]
[--hp-exit]
optional arguments:
-h, --help show this help message and exit
--weight-decay WEIGHT_DECAY
(default: 1e-05)
--hp-save HP_SAVE Save hyperparameters to a file. The hyperparameters
are saved after processing of all other options
(default: None)
--hp-load HP_LOAD Load hyperparameters from a file. The hyperparameters
are loaded before any other options are processed
(default: None)
--hp-list [{detail,yaml,json}]
List all available hyperparameters. If `--hp-list
detail` is specified, a verbose table will be print
(default: None)
--hp-detail Shorthand for --hp-list detail (default: False)
--hp-serial-format {auto,yaml,pickle}
Format of the saved config file. Defaults to auto. It
can be set to override auto file type deduction.
(default: auto)
--hp-exit process all hpargparse actions and quit (default:
False)
Besides using hpargparse.bind
in you code, we also come with a command line
tool hpcli
to provide similar functions to any existing file using hpman.
src.py
from hpman.m import _
_('num_channels', 128)
_('num_layers', 50)
In shell:
$ hpcli src.py
num_channels: 128
num_layers: 50
$ hpcli src.py --num-layers 101
num_channels: 128
num_layers: 101
$ hpcli src.py --num-layers 101 --hp-save config.yaml
num_channels: 128
num_layers: 101
$ hpcli src.py --num-layers 101 --hp-save config.yaml --hp-list detail
All hyperparameters:
['num_channels', 'num_layers']
Details
ββββββββββββββββ¦βββββββ¦ββββββββ¦ββββββββββββββββββββββββββββββββββββββββ
β name β type β value β details β
β βββββββββββββββ¬βββββββ¬ββββββββ¬ββββββββββββββββββββββββββββββββββββββββ£
β num_channels β int β 128 β occurrence[0]: β
β β β β src.py:3 β
β β β β 1: from hpman.m import _ β
β β β β 2: β
β β β β ==> 3: _("num_channels", 128) β
β β β β 4: _("num_layers", 50) β
β β β β 5: β
β βββββββββββββββ¬βββββββ¬ββββββββ¬ββββββββββββββββββββββββββββββββββββββββ£
β num_layers β int β 101 β occurrence[0]: β
β β β β src.py:4 β
β β β β 1: from hpman.m import _ β
β β β β 2: β
β β β β 3: _("num_channels", 128) β
β β β β ==> 4: _("num_layers", 50) β
β β β β 5: β
ββββββββββββββββ©βββββββ©ββββββββ©ββββββββββββββββββββββββββββββββββββββββ
$ hpcli src.py -h
usage: hpcli [-h] [--num-channels NUM_CHANNELS] [--num-layers NUM_LAYERS]
[--hp-save HP_SAVE] [--hp-load HP_LOAD]
[--hp-list [{detail,yaml,json}]] [--hp-detail]
[--hp-serial-format {auto,yaml,pickle}] [--hp-exit]
optional arguments:
-h, --help show this help message and exit
--num-channels NUM_CHANNELS
(default: 128)
--num-layers NUM_LAYERS
(default: 50)
--hp-save HP_SAVE Save hyperparameters to a file. The hyperparameters
are saved after processing of all other options
(default: None)
--hp-load HP_LOAD Load hyperparameters from a file. The hyperparameters
are loaded before any other options are processed
(default: None)
--hp-list [{detail,yaml,json}]
List all available hyperparameters. If `--hp-list
detail` is specified, a verbose table will be print
(default: yaml)
--hp-detail Shorthand for --hp-list detail (default: False)
--hp-serial-format {auto,yaml,pickle}
Format of the saved config file. Defaults to auto. It
can be set to override auto file type deduction.
(default: auto)
--hp-exit process all hpargparse actions and quit (default:
False)
This could be a handy tool to inspect the hyperparameters in your code.
This example lies in examples/01-nn-training.
It is a fully functional example of training a LeNet on MNIST using
hpargparse
and hpman
collaboratively to manage hyperparameters.
We highly suggest you playing around this example.
Now we break down the functions one-by-one.
The following example lies in examples/00-basic.
lib.py
:
from hpman.m import _
def add():
return _("a", 1) + _("b", 2)
def mult():
return _("a") * _("b")
main.py
#!/usr/bin/env python3
import argparse
import hpargparse
from hpman.m import _
import os
BASE_DIR = os.path.dirname(os.path.realpath(__file__))
def main():
parser = argparse.ArgumentParser()
# ... do whatever you want
parser.add_argument(dest="predefined_arg")
# analyze everything in this directory
_.parse_file(BASE_DIR) # <-- IMPORTANT
# bind will monkey_patch parser.parse_args to do its job
hpargparse.bind(parser, _) # <-- IMPORTANT
# parse args and set the values
args = parser.parse_args()
# ... do whatever you want next
import lib
print("a = {}".format(_.get_value("a")))
print("b = {}".format(_.get_value("b")))
print("lib.add() = {}".format(lib.add()))
print("lib.mult() = {}".format(lib.mult()))
if __name__ == "__main__":
main()
$ ./main.py -h
usage: main.py [-h] [--a A] [--b B] [--hp-save HP_SAVE] [--hp-load HP_LOAD]
[--hp-list [{detail,yaml,json}]] [--hp-detail]
[--hp-serial-format {auto,yaml,pickle}] [--hp-exit]
predefined_arg
positional arguments:
predefined_arg
optional arguments:
-h, --help show this help message and exit
--a A (default: 1)
--b B (default: 2)
--hp-save HP_SAVE Save hyperparameters to a file. The hyperparameters
are saved after processing of all other options
(default: None)
--hp-load HP_LOAD Load hyperparameters from a file. The hyperparameters
are loaded before any other options are processed
(default: None)
--hp-list [{detail,yaml,json}]
List all available hyperparameters. If `--hp-list
detail` is specified, a verbose table will be print
(default: None)
--hp-detail Shorthand for --hp-list detail (default: False)
--hp-serial-format {auto,yaml,pickle}
Format of the saved config file. Defaults to auto. It
can be set to override auto file type deduction.
(default: auto)
--hp-exit process all hpargparse actions and quit (default:
False)
$ ./main.py some_thing --a 3 --b 5
a = 3
b = 5
lib.add() = 8
lib.mult() = 15
$ ./main.py some_arg --hp-list
a: 1
b: 2
... and details:
$ ./main.py some_arg --hp-list detail
All hyperparameters:
['a', 'b']
Details
ββββββββ¦βββββββ¦ββββββββ¦ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β name β type β value β details β
β βββββββ¬βββββββ¬ββββββββ¬ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ£
β a β int β 1 β occurrence[0]: β
β β β β /data/project/hpargparse/examples/00-basic/lib.py:8 β
β β β β 3: # for more usecases, please refer to hpman's document β
β β β β 4: β
β β β β 5: β
β β β β 6: def add(): β
β β β β 7: # define a hyperparameter on-the-fly with defaults β
β β β β ==> 8: return _("a", 1) + _("b", 2) β
β β β β 9: β
β β β β 10: β
β β β β 11: def mult(): β
β β β β 12: # reuse a pre-defined hyperparameters β
β β β β 13: return _("a") * _("b") β
β β β β occurrence[1]: β
β β β β /data/project/hpargparse/examples/00-basic/lib.py:13 β
β β β β 8: return _("a", 1) + _("b", 2) β
β β β β 9: β
β β β β 10: β
β β β β 11: def mult(): β
β β β β 12: # reuse a pre-defined hyperparameters β
β β β β ==> 13: return _("a") * _("b") β
β β β β 14: β
β βββββββ¬βββββββ¬ββββββββ¬ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ£
β b β int β 2 β occurrence[0]: β
β β β β /data/project/hpargparse/examples/00-basic/lib.py:8 β
β β β β 3: # for more usecases, please refer to hpman's document β
β β β β 4: β
β β β β 5: β
β β β β 6: def add(): β
β β β β 7: # define a hyperparameter on-the-fly with defaults β
β β β β ==> 8: return _("a", 1) + _("b", 2) β
β β β β 9: β
β β β β 10: β
β β β β 11: def mult(): β
β β β β 12: # reuse a pre-defined hyperparameters β
β β β β 13: return _("a") * _("b") β
β β β β occurrence[1]: β
β β β β /data/project/hpargparse/examples/00-basic/lib.py:13 β
β β β β 8: return _("a", 1) + _("b", 2) β
β β β β 9: β
β β β β 10: β
β β β β 11: def mult(): β
β β β β 12: # reuse a pre-defined hyperparameters β
β β β β ==> 13: return _("a") * _("b") β
β β β β 14: β
ββββββββ©βββββββ©ββββββββ©ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
# save to yaml file
$ ./main.py some_arg --hp-save /tmp/config.yaml --hp-exit
$ cat /tmp/config.yaml
a: 1
b: 2
# load from yaml file
$ cat config_modified.yaml
a: 123
b: 456
$ ./main.py some_arg --hp-load config_modified.yaml --hp-list
a: 123
b: 456
- Install requirements:
pip install -r requirements.dev.txt -r requirements.txt
- Activate git commit template
git config commit.template .git-commit-template.txt
- Install pre-commit hook
pre-commit install