print rational numbers using the rdiv operator when defined (#413)
This commit is contained in:
@@ -789,6 +789,13 @@ impl<'a> TryFrom<&'a HeapCellValue> for Number {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl<'a> From<&'a Integer> for Number {
|
||||||
|
#[inline]
|
||||||
|
fn from(src: &'a Integer) -> Self {
|
||||||
|
Number::Integer(Rc::new(Integer::from(src)))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Computes n ^ power. Ignores the sign of power.
|
// Computes n ^ power. Ignores the sign of power.
|
||||||
pub fn binary_pow(mut n: Integer, power: &Integer) -> Integer {
|
pub fn binary_pow(mut n: Integer, power: &Integer) -> Integer {
|
||||||
let mut power = Integer::from(power.abs_ref());
|
let mut power = Integer::from(power.abs_ref());
|
||||||
|
|||||||
@@ -7,7 +7,7 @@ use crate::prolog::machine::heap::*;
|
|||||||
use crate::prolog::machine::machine_indices::*;
|
use crate::prolog::machine::machine_indices::*;
|
||||||
use crate::prolog::machine::machine_state::*;
|
use crate::prolog::machine::machine_state::*;
|
||||||
use crate::prolog::ordered_float::OrderedFloat;
|
use crate::prolog::ordered_float::OrderedFloat;
|
||||||
use crate::prolog::rug::Integer;
|
use crate::prolog::rug::{Integer, Rational};
|
||||||
|
|
||||||
use indexmap::{IndexMap, IndexSet};
|
use indexmap::{IndexMap, IndexSet};
|
||||||
|
|
||||||
@@ -170,6 +170,7 @@ enum TokenOrRedirect {
|
|||||||
NumberedVar(String),
|
NumberedVar(String),
|
||||||
CompositeRedirect(usize, DirectedOp),
|
CompositeRedirect(usize, DirectedOp),
|
||||||
FunctorRedirect(usize),
|
FunctorRedirect(usize),
|
||||||
|
Number(Number, Option<DirectedOp>),
|
||||||
Open,
|
Open,
|
||||||
Close,
|
Close,
|
||||||
Comma,
|
Comma,
|
||||||
@@ -989,6 +990,10 @@ impl<'a, Outputter: HCValueOutputter> HCPrinter<'a, Outputter> {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Number::Rational(r) => {
|
||||||
|
self.print_rational(&r, add_brackets);
|
||||||
|
return;
|
||||||
|
}
|
||||||
n => {
|
n => {
|
||||||
let output_str = format!("{}", n);
|
let output_str = format!("{}", n);
|
||||||
|
|
||||||
@@ -1003,6 +1008,71 @@ impl<'a, Outputter: HCValueOutputter> HCPrinter<'a, Outputter> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn print_rational(&mut self, r: &Rational, add_brackets: bool) {
|
||||||
|
match self.op_dir.get(&(clause_name!("rdiv"), Fixity::In)) {
|
||||||
|
Some(OpDirValue(ref spec, _)) => {
|
||||||
|
if add_brackets {
|
||||||
|
self.state_stack.push(TokenOrRedirect::Close);
|
||||||
|
}
|
||||||
|
|
||||||
|
let rdiv_ct = clause_name!("rdiv");
|
||||||
|
|
||||||
|
let left_directed_op =
|
||||||
|
if spec.prec() > 0 {
|
||||||
|
Some(DirectedOp::Left(rdiv_ct.clone(), spec.clone()))
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
};
|
||||||
|
|
||||||
|
let right_directed_op =
|
||||||
|
if spec.prec() > 0 {
|
||||||
|
Some(DirectedOp::Right(rdiv_ct.clone(), spec.clone()))
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
};
|
||||||
|
|
||||||
|
if spec.prec() > 0 {
|
||||||
|
self.state_stack.push(TokenOrRedirect::Number(
|
||||||
|
Number::from(r.denom()),
|
||||||
|
left_directed_op,
|
||||||
|
));
|
||||||
|
|
||||||
|
self.state_stack.push(TokenOrRedirect::Op(
|
||||||
|
rdiv_ct,
|
||||||
|
spec.clone(),
|
||||||
|
));
|
||||||
|
|
||||||
|
self.state_stack.push(TokenOrRedirect::Number(
|
||||||
|
Number::from(r.numer()),
|
||||||
|
right_directed_op,
|
||||||
|
));
|
||||||
|
} else {
|
||||||
|
self.state_stack.push(TokenOrRedirect::Close);
|
||||||
|
|
||||||
|
self.state_stack.push(TokenOrRedirect::Number(
|
||||||
|
Number::from(r.denom()),
|
||||||
|
None,
|
||||||
|
));
|
||||||
|
|
||||||
|
self.state_stack.push(TokenOrRedirect::Comma);
|
||||||
|
|
||||||
|
self.state_stack.push(TokenOrRedirect::Number(
|
||||||
|
Number::from(r.numer()),
|
||||||
|
None,
|
||||||
|
));
|
||||||
|
|
||||||
|
self.state_stack.push(TokenOrRedirect::Open);
|
||||||
|
self.state_stack.push(TokenOrRedirect::Atom(rdiv_ct));
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
_ => {
|
||||||
|
unreachable!()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn print_char(&mut self, is_quoted: bool, c: char)
|
fn print_char(&mut self, is_quoted: bool, c: char)
|
||||||
{
|
{
|
||||||
if non_quoted_token(once(c)) {
|
if non_quoted_token(once(c)) {
|
||||||
@@ -1431,6 +1501,7 @@ impl<'a, Outputter: HCValueOutputter> HCPrinter<'a, Outputter> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
TokenOrRedirect::HeadTailSeparator => self.append_str("|"),
|
TokenOrRedirect::HeadTailSeparator => self.append_str("|"),
|
||||||
|
TokenOrRedirect::Number(n, op) => self.print_number(n, &op),
|
||||||
TokenOrRedirect::Comma => self.append_str(","),
|
TokenOrRedirect::Comma => self.append_str(","),
|
||||||
TokenOrRedirect::Space => self.push_char(' '),
|
TokenOrRedirect::Space => self.push_char(' '),
|
||||||
TokenOrRedirect::LeftCurly => self.push_char('{'),
|
TokenOrRedirect::LeftCurly => self.push_char('{'),
|
||||||
|
|||||||
Reference in New Issue
Block a user