forked from github/server
more fractions functionality.
This commit is contained in:
parent
e0229be500
commit
e557140ad1
|
@ -4,6 +4,9 @@
|
||||||
#include <assert.h>
|
#include <assert.h>
|
||||||
#include <limits.h>
|
#include <limits.h>
|
||||||
|
|
||||||
|
const variant frac_zero = { .sa = { 0, 1 } };
|
||||||
|
const variant frac_one = { .sa = { 1, 1 } };
|
||||||
|
|
||||||
static int gcd(int a, int b) {
|
static int gcd(int a, int b) {
|
||||||
const int primes[] = { 3, 5, 7, 11, 13, 17, 19, 23, 0 };
|
const int primes[] = { 3, 5, 7, 11, 13, 17, 19, 23, 0 };
|
||||||
int i = 0, g = 1, p = 2;
|
int i = 0, g = 1, p = 2;
|
||||||
|
@ -28,6 +31,10 @@ static int lcm(int a, int b) {
|
||||||
return x;
|
return x;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool frac_equal(variant a, variant b) {
|
||||||
|
return frac_sign(frac_sub(a, b)) == 0;
|
||||||
|
}
|
||||||
|
|
||||||
variant frac_make(int num, int den)
|
variant frac_make(int num, int den)
|
||||||
{
|
{
|
||||||
variant v;
|
variant v;
|
||||||
|
@ -64,3 +71,10 @@ variant frac_div(variant a, variant b)
|
||||||
{
|
{
|
||||||
return frac_make(a.sa[0] * b.sa[1], a.sa[1] * b.sa[0]);
|
return frac_make(a.sa[0] * b.sa[1], a.sa[1] * b.sa[0]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int frac_sign(variant a) {
|
||||||
|
if (a.sa[0] == 0) return 0;
|
||||||
|
if (a.sa[0] > 0 && a.sa[1] > 0) return 1;
|
||||||
|
if (a.sa[0] < 0 && a.sa[1] < 0) return 1;
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
|
@ -2,6 +2,9 @@
|
||||||
|
|
||||||
#ifndef STRUCT_VARIANT_H
|
#ifndef STRUCT_VARIANT_H
|
||||||
#define STRUCT_VARIANT_H
|
#define STRUCT_VARIANT_H
|
||||||
|
|
||||||
|
#include <stdbool.h>
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
extern "C" {
|
extern "C" {
|
||||||
#endif
|
#endif
|
||||||
|
@ -21,11 +24,16 @@ extern "C" {
|
||||||
VAR_FLOAT
|
VAR_FLOAT
|
||||||
} variant_type;
|
} variant_type;
|
||||||
|
|
||||||
|
extern const variant frac_zero;
|
||||||
|
extern const variant frac_one;
|
||||||
|
|
||||||
variant frac_make(int num, int den);
|
variant frac_make(int num, int den);
|
||||||
variant frac_add(variant a, variant b);
|
variant frac_add(variant a, variant b);
|
||||||
variant frac_sub(variant a, variant b);
|
variant frac_sub(variant a, variant b);
|
||||||
variant frac_mul(variant a, variant b);
|
variant frac_mul(variant a, variant b);
|
||||||
variant frac_div(variant a, variant b);
|
variant frac_div(variant a, variant b);
|
||||||
|
int frac_sign(variant a);
|
||||||
|
bool frac_equal(variant a, variant b);
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,8 +20,16 @@ static void test_fractions(CuTest *tc) {
|
||||||
CuAssertIntEquals(tc, 1, a.sa[1]);
|
CuAssertIntEquals(tc, 1, a.sa[1]);
|
||||||
a = frac_sub(a, a);
|
a = frac_sub(a, a);
|
||||||
CuAssertIntEquals(tc, 0, a.sa[0]);
|
CuAssertIntEquals(tc, 0, a.sa[0]);
|
||||||
a = frac_mul(a, b);
|
a = frac_sub(frac_one, a);
|
||||||
|
CuAssertIntEquals(tc, 1, a.sa[0]);
|
||||||
|
CuAssertIntEquals(tc, 1, a.sa[1]);
|
||||||
|
a = frac_mul(a, frac_zero);
|
||||||
CuAssertIntEquals(tc, 0, a.sa[0]);
|
CuAssertIntEquals(tc, 0, a.sa[0]);
|
||||||
|
CuAssertIntEquals(tc, 1, frac_sign(frac_make(-1, -1)));
|
||||||
|
CuAssertIntEquals(tc, 1, frac_sign(frac_make(1, 1)));
|
||||||
|
CuAssertIntEquals(tc, -1, frac_sign(frac_make(-1, 1)));
|
||||||
|
CuAssertIntEquals(tc, -1, frac_sign(frac_make(1, -1)));
|
||||||
|
CuAssertIntEquals(tc, 0, frac_sign(frac_make(0, 1)));
|
||||||
}
|
}
|
||||||
|
|
||||||
CuSuite *get_variant_suite(void)
|
CuSuite *get_variant_suite(void)
|
||||||
|
|
Loading…
Reference in New Issue