[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: Kludge for handling REPL arithmetic expressions
From: |
Eric Pruitt |
Subject: |
Re: Kludge for handling REPL arithmetic expressions |
Date: |
Wed, 4 Aug 2021 08:36:41 -0700 |
User-agent: |
Mutt/1.10.1 (2018-07-13) |
On Wed, Aug 04, 2021 at 11:12:01AM +0100, Chris Elvidge wrote:
> On 03/08/2021 04:32 am, Eric Pruitt wrote:
> > I have a command setup in Bash that allows me to use "=" to do
> > arithmetic in an interactive session:
> >
> > ~$ = 1/42 * 9
> > 0.2142857142857143 (3/14)
> > ~$ = log(2048, 2)
> > 11
> > ~$ = 1/3 + 7
> > 7.333333333333333 (22/3)
> > ~$ = x * 3
> > 22
>
> I was intrigued by this. So tried:
> =() { echo "scale=5; $@" | bc; }
> as an experiment.
> Seems to work for simple calculations.
>
> A couple of questions, though.
> 1) How do you 'export -f ='? Or is it impossible?
> 2) How do you type in '= log(2048,2)' without getting a syntax error?
You can find my bashrc at
<https://github.com/ericpruitt/emus/blob/master/configuration/bashrc>.
The relevant bits are:
...
BASH_ALIASES[=]='calculate #'
...
# Handler used to intercept arithmetic expressions so they can be
# entered without having to add a space after the "=".
#
function command_not_found_handle()
{
if [[ "$1" != =* ]]; then
printf "%s: command not found\n" "$1" >&2
return 127
fi
eval "= ${1#=} ${@:2}"
}
# Handler used to intercept arithmetic expressions so they can be
# entered without having to add a space after the "=".
#
function no_such_file_handle()
{
if [[ "$1" != =* ]]; then
printf "%s: No such file or directory\n" "$1" >&2
return 127
fi
eval "= ${1#=} ${@:2}"
}
# Calculate the result of an expression. The result of the last
# successfully evaluated expression is made available as the
# variable "x". The expression must appear in the command history to
# be evaluated.
#
function calculate()
{
local result
result="$(
expression="$(HISTTIMEFORMAT= \history 1)"
pc "x = $LAST_RESULT" "$(eval "echo \" ${expression#*=}\"")"
)"
test -n "$result" && LAST_RESULT="${result#* }" && echo "$result"
}
The "pc" command is a script I created that uses Python as an
alternative to "bc" which you can find at
<https://github.com/ericpruitt/emus/blob/master/scripts/pc>. The script
represents rational numbers as fractions internally to reduce floating
point errors:
$ python3 -c "print(1/9 * 7 + 2/9)"
0.9999999999999999
$ bc <<< "1/9 * 7 + 2/9"
.99999999999999999999
$ pc "1/9 * 7 + 2/9"
1
Eric