Скачиваний:
62
Добавлен:
01.05.2014
Размер:
4.53 Кб
Скачать
// Fraction.cpp: implementation of the Fraction class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "Fraction.h"
#include <iostream.h>
#include <math.h>

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

Fraction::~Fraction()
{

}

Fraction::Fraction()
{
	integral = 0;
	numerator = 0;
	denominator = 1;
}


Fraction::Fraction(int a)
{
	integral = 0;
	numerator = a;
	denominator = 1;
}


Fraction::Fraction(int a, int b)
{
	integral = 0;
	numerator = a;
	denominator = b;
	normalize();

}



Fraction::Fraction(int i, int a, int b)
{
	integral = i;
	numerator = a;
	denominator = b;
	normalize();
}

void Fraction::write()
{
	// Выводим целую часть только тогда, когда она не равна нулю
	if (integral != 0)
		cout << integral << " ";
	if (numerator != 0) {
		// Если целая часть меньше 0, то перед дробной частью знак "-" не выводим
		cout << (integral >= 0? numerator: -numerator) << "/" << denominator;
	}
	
	if (integral == 0 && numerator == 0)
		cout << 0;

}

void Fraction::normalize()
{
	denormalize();
	// Знак хранится только в числителе
	if (denominator < 0) {
		numerator = -numerator;
		denominator = -denominator;

	}
	// выделяем целую часть
	integral += numerator / denominator;
	numerator = numerator % denominator;
	
	// Ищем НОД числителя и знаменателя, используя алгоритм Евклида
	int a, b, c;
	a = abs(numerator);
	b = denominator;
	while (a > 0) {
		b %= a; // Остаток от деления b / a
		// Меняем значения в переменных a и b местами
		c = a;
		a = b;
		b = c;
	}
	// Сокращаем дробь
	numerator /= b;
	denominator /= b;
}

void Fraction::denormalize()
{
	numerator += integral * denominator;
	integral = 0;

}

Fraction Fraction::operator +(const Fraction& b)
{
	Fraction r(integral, numerator, denominator), b1(b.integral, b.numerator, b.denominator);
	// Избавляемся от целой части, записывая её в числитель дроби a b/c = (ac + b) / c
	r.denormalize();
	b1.denormalize();
	// складываем по правилу a/b + c/d = (ad + bc)/ bd
	r.numerator = r.numerator * b1.denominator + b1.numerator * r.denominator;
	r.denominator = r.denominator * b1.denominator;
	r.normalize();
	return r;
}

Fraction Fraction::operator -(const Fraction &b)
{
	Fraction r(integral, numerator, denominator), b1(b.integral, b.numerator, b.denominator);
	// Избавляемся от целой части, записывая её в числитель дроби a b/c = (ac + b) / c
	r.denormalize();
	b1.denormalize();
	// вычитаем по правилу a/b - c/d = (ad - bc)/ bd
	r.numerator = r.numerator * b1.denominator - b1.numerator * r.denominator;
	r.denominator = r.denominator * b1.denominator;
	r.normalize();
	return r;
}

Fraction operator* (const Fraction& a, const Fraction& b)
{
	Fraction r(a.integral, a.numerator, a.denominator), b1(b.integral, b.numerator, b.denominator);
	// Избавляемся от целой части, записывая её в числитель дроби a b/c = (ac + b) / c
	r.denormalize();
	b1.denormalize();
	// Умножаем по правилу a/b * c/d = ac / bd
	r.numerator = r.numerator * b1.numerator;
	r.denominator = r.denominator * b1.denominator;
	r.normalize();
	return r;
}

Fraction operator/ (const Fraction& a, const Fraction& b)
{
	Fraction r(a.integral, a.numerator, a.denominator), b1(b.integral, b.numerator, b.denominator);
	// Избавляемся от целой части, записывая её в числитель дроби a b/c = (ac + b) / c
	r.denormalize();
	b1.denormalize();
	// Делим по правилу a/b / c/d = ad / bc
	int n, d;
	n = r.numerator * b1.denominator;
	d = r.denominator * b1.numerator;
	r.numerator = n;
	r.denominator = d;
	r.normalize();
	return r;

}

Fraction Fraction::operator =(const Fraction &b)
{
	// Присваиваем 
	integral = b.integral;
	numerator = b.numerator;
	denominator = b.denominator;
	return *this;
}

bool operator == (const Fraction& a, const Fraction& b)
{
	// Так как дробь может храниться только в нормальном виде
	// (все операции и конструкторы явно это делают)
	// просто сравниваем все части
	return a.integral == b.integral
			&& a.numerator == b.numerator
			&& a.denominator == b.denominator;
}

// Префиксный ++
Fraction Fraction::operator ++()
{
	numerator = 0;
	return *this;
}

// Постфиксный ++
Fraction Fraction::operator ++(int a)
{
	Fraction r = *this;
	numerator = 0;
	return r;

}
Соседние файлы в папке prj2