--- a/Fraction.st Thu Dec 07 22:32:49 1995 +0100
+++ b/Fraction.st Thu Dec 07 22:38:49 1995 +0100
@@ -11,10 +11,10 @@
"
Number subclass:#Fraction
- instanceVariableNames:'numerator denominator'
- classVariableNames:'FractionOne FractionZero'
- poolDictionaries:''
- category:'Magnitude-Numbers'
+ instanceVariableNames:'numerator denominator'
+ classVariableNames:'FractionOne FractionZero'
+ poolDictionaries:''
+ category:'Magnitude-Numbers'
!
!Fraction class methodsFor:'documentation'!
@@ -33,10 +33,6 @@
"
!
-version
- ^ '$Header: /cvs/stx/stx/libbasic/Fraction.st,v 1.24 1995-11-11 15:23:22 cg Exp $'
-!
-
documentation
"
Instances of Fraction represent fractional numbers consisting of
@@ -54,20 +50,6 @@
]
! !
-!Fraction class methodsFor:'constants'!
-
-zero
- "return the neutral element for addition"
-
- ^ FractionZero
-!
-
-unity
- "return the neutral element for multiplication"
-
- ^ FractionOne
-! !
-
!Fraction class methodsFor:'instance creation'!
new
@@ -104,6 +86,20 @@
^ self basicNew setNumerator:num denominator:den
! !
+!Fraction class methodsFor:'constants'!
+
+unity
+ "return the neutral element for multiplication"
+
+ ^ FractionOne
+!
+
+zero
+ "return the neutral element for addition"
+
+ ^ FractionZero
+! !
+
!Fraction class methodsFor:'queries'!
isBuiltInClass
@@ -112,157 +108,42 @@
^ self == Fraction
! !
-!Fraction methodsFor:'queries'!
-
-isFraction
- "return true, if the receiver is some kind of fraction;
- true is returned here - the method is redefined from Object."
-
- ^ true
-! !
-
!Fraction methodsFor:'accessing'!
-numerator
- "return the numerator"
-
- ^ numerator
-!
-
denominator
"return the denominator"
^ denominator
-! !
-
-!Fraction methodsFor:'private'!
-
-setNumerator:num denominator:den
- "set both numerator and denominator"
-
- numerator := num.
- denominator := den
-!
-
-reduced
- "reduce the receiver"
-
- |gc|
-
- denominator == 1 ifTrue:[^ numerator].
- numerator == 1 ifTrue:[^ self].
- numerator == 0 ifTrue:[^ 0].
-
- gc := numerator gcd:denominator.
- (gc == 1) ifFalse:[
- numerator := numerator // gc.
- denominator := denominator // gc
- ].
- (numerator < 0) ifTrue:[
- (denominator < 0) ifTrue:[
- numerator := numerator negated.
- denominator := denominator negated
- ]
- ].
- (denominator == 1) ifTrue:[^ numerator].
- ^ self
-! !
-
-!Fraction methodsFor:'coercing & converting'!
-
-coerce:aNumber
- "return aNumber converted into receivers type"
-
- ^ aNumber asFraction
-!
-
-generality
- "return the generality value - see ArithmeticValue>>retry:coercing:"
-
- ^ 60
-!
-
-asInteger
- "return an integer with my value - will usually truncate"
-
- ^ numerator // denominator
-!
-
-asLargeInteger
- "return an integer with my value - will usually truncate"
-
- ^ self asInteger asLargeInteger
!
-asFloat
- "return a float with (approximately) my value"
-
- ^ (numerator asFloat) / (denominator asFloat)
-!
-
-asFraction
- "return the receiver as fraction - thats itself"
-
- ^ self
-! !
-
-!Fraction methodsFor:'comparing'!
-
-= aNumber
- "return true, if the argument represents the same numeric value
- as the receiver, false otherwise"
-
- (aNumber isMemberOf:SmallInteger) ifTrue:[
- (denominator = 1) ifFalse:[^ false].
- ^ numerator = aNumber
- ].
- aNumber isFraction ifTrue:[
- (numerator = aNumber numerator) ifFalse:[^ false].
- ^ denominator = aNumber denominator
- ].
- ^ self retry:#= coercing:aNumber
-!
+numerator
+ "return the numerator"
-> aNumber
- "return true if the receiver is greater
- than aNumber, false otherwise."
- "optional - could use inherited method ..."
-
- (aNumber isMemberOf:SmallInteger) ifTrue:[
- ^ numerator > (denominator * aNumber)
- ].
- aNumber isFraction ifTrue:[
- ^ (numerator * aNumber denominator) > (denominator * aNumber numerator)
- ].
- ^ self retry:#> coercing:aNumber
-!
-
-< aNumber
- "return true if the receiver is less
- than aNumber, false otherwise."
-
- (aNumber isMemberOf:SmallInteger) ifTrue:[
- ^ numerator < (denominator * aNumber)
- ].
- aNumber isFraction ifTrue:[
- ^ (numerator * aNumber denominator) < (denominator * aNumber numerator)
- ].
- ^ aNumber lessFromFraction:self
-! !
-
-!Fraction methodsFor:'testing'!
-
-negative
- "return true if the receiver is negative"
-
- (numerator < 0) ifTrue:[
- ^ (denominator < 0) not
- ].
- ^ (denominator < 0)
+ ^ numerator
! !
!Fraction methodsFor:'arithmetic'!
+* aNumber
+ "return the product of the receiver and the argument, aNumber"
+
+ |n d|
+
+ (aNumber isMemberOf:SmallInteger) ifTrue:[
+ ^ (self class numerator:(numerator * aNumber)
+ denominator:denominator) reduced
+ ].
+ aNumber isFraction ifTrue:[
+ n := numerator * aNumber numerator.
+ d := denominator * aNumber denominator.
+ ^ (self class numerator:n denominator:d) reduced
+ ].
+ (aNumber isMemberOf:Float) ifTrue:[
+ ^ (numerator * aNumber) / denominator
+ ].
+ ^ aNumber productFromFraction:self
+!
+
+ aNumber
"return the sum of the receiver and the argument, aNumber"
@@ -317,26 +198,6 @@
^ aNumber differenceFromFraction:self
!
-* aNumber
- "return the product of the receiver and the argument, aNumber"
-
- |n d|
-
- (aNumber isMemberOf:SmallInteger) ifTrue:[
- ^ (self class numerator:(numerator * aNumber)
- denominator:denominator) reduced
- ].
- aNumber isFraction ifTrue:[
- n := numerator * aNumber numerator.
- d := denominator * aNumber denominator.
- ^ (self class numerator:n denominator:d) reduced
- ].
- (aNumber isMemberOf:Float) ifTrue:[
- ^ (numerator * aNumber) / denominator
- ].
- ^ aNumber productFromFraction:self
-!
-
/ aNumber
"return the quotient of the receiver and the argument, aNumber"
@@ -381,30 +242,94 @@
denominator:numerator
! !
-!Fraction methodsFor:'truncation and rounding'!
+!Fraction methodsFor:'coercing & converting'!
+
+asFloat
+ "return a float with (approximately) my value"
+
+ ^ (numerator asFloat) / (denominator asFloat)
+!
-truncated
- "return the receiver truncated towards zero as Integer"
+asFraction
+ "return the receiver as fraction - thats itself"
+
+ ^ self
+!
+
+asInteger
+ "return an integer with my value - will usually truncate"
^ numerator // denominator
!
-rounded
- "return the receiver rounded to the nearest integer as integer"
+asLargeInteger
+ "return an integer with my value - will usually truncate"
+
+ ^ self asInteger asLargeInteger
+!
+
+coerce:aNumber
+ "return aNumber converted into receivers type"
+
+ ^ aNumber asFraction
+!
+
+generality
+ "return the generality value - see ArithmeticValue>>retry:coercing:"
+
+ ^ 60
+! !
+
+!Fraction methodsFor:'comparing'!
+
+< aNumber
+ "return true if the receiver is less
+ than aNumber, false otherwise."
- self negative ifTrue:[
- ^ (self + (1/2)) truncated - 1
+ (aNumber isMemberOf:SmallInteger) ifTrue:[
+ ^ numerator < (denominator * aNumber)
+ ].
+ aNumber isFraction ifTrue:[
+ ^ (numerator * aNumber denominator) < (denominator * aNumber numerator)
+ ].
+ ^ aNumber lessFromFraction:self
+!
+
+= aNumber
+ "return true, if the argument represents the same numeric value
+ as the receiver, false otherwise"
+
+ (aNumber isMemberOf:SmallInteger) ifTrue:[
+ (denominator = 1) ifFalse:[^ false].
+ ^ numerator = aNumber
].
- ^ (self + (1/2)) truncated
+ aNumber isFraction ifTrue:[
+ (numerator = aNumber numerator) ifFalse:[^ false].
+ ^ denominator = aNumber denominator
+ ].
+ ^ self retry:#= coercing:aNumber
+!
+
+> aNumber
+ "return true if the receiver is greater
+ than aNumber, false otherwise."
+ "optional - could use inherited method ..."
+
+ (aNumber isMemberOf:SmallInteger) ifTrue:[
+ ^ numerator > (denominator * aNumber)
+ ].
+ aNumber isFraction ifTrue:[
+ ^ (numerator * aNumber denominator) > (denominator * aNumber numerator)
+ ].
+ ^ self retry:#> coercing:aNumber
! !
!Fraction methodsFor:'double dispatching'!
-sumFromInteger:anInteger
- "sent when an integer does not know how to add the receiver, a fraction"
+differenceFromFloat:aFloat
+ "sent when a float does not know how to subtract the receiver, a fraction"
- ^ (self class numerator:(numerator + (anInteger * denominator))
- denominator:denominator) reduced
+ ^ (aFloat * denominator - numerator) / denominator
!
differenceFromInteger:anInteger
@@ -414,6 +339,18 @@
denominator:denominator) reduced
!
+lessFromInteger:anInteger
+ "sent when an integer does not know how to compare to the receiver, a fraction"
+
+ ^ (denominator * anInteger) < numerator
+!
+
+productFromFloat:aFloat
+ "sent when a float does not know how to multiply the receiver, a fraction"
+
+ ^ aFloat * numerator / denominator
+!
+
productFromInteger:anInteger
"sent when an integer does not know how to multiply the receiver, a fraction"
@@ -421,6 +358,12 @@
denominator:denominator) reduced
!
+quotientFromFloat:aFloat
+ "sent when a float does not know how to divide by the receiver, a fraction"
+
+ ^ (aFloat * denominator) / numerator
+!
+
quotientFromInteger:anInteger
"sent when an integer does not know how to divide by the receiver, a fraction"
@@ -428,34 +371,17 @@
denominator:numerator) reduced
!
-lessFromInteger:anInteger
- "sent when an integer does not know how to compare to the receiver, a fraction"
-
- ^ (denominator * anInteger) < numerator
-!
-
sumFromFloat:aFloat
"sent when a float does not know how to add the receiver, a fraction"
^ (aFloat * denominator + numerator) / denominator
!
-differenceFromFloat:aFloat
- "sent when a float does not know how to subtract the receiver, a fraction"
-
- ^ (aFloat * denominator - numerator) / denominator
-!
+sumFromInteger:anInteger
+ "sent when an integer does not know how to add the receiver, a fraction"
-productFromFloat:aFloat
- "sent when a float does not know how to multiply the receiver, a fraction"
-
- ^ aFloat * numerator / denominator
-!
-
-quotientFromFloat:aFloat
- "sent when a float does not know how to divide by the receiver, a fraction"
-
- ^ (aFloat * denominator) / numerator
+ ^ (self class numerator:(numerator + (anInteger * denominator))
+ denominator:denominator) reduced
! !
!Fraction methodsFor:'printing & storing'!
@@ -470,3 +396,80 @@
denominator printOn:aStream.
aStream nextPut:$)
! !
+
+!Fraction methodsFor:'private'!
+
+reduced
+ "reduce the receiver"
+
+ |gc|
+
+ denominator == 1 ifTrue:[^ numerator].
+ numerator == 1 ifTrue:[^ self].
+ numerator == 0 ifTrue:[^ 0].
+
+ gc := numerator gcd:denominator.
+ (gc == 1) ifFalse:[
+ numerator := numerator // gc.
+ denominator := denominator // gc
+ ].
+ (numerator < 0) ifTrue:[
+ (denominator < 0) ifTrue:[
+ numerator := numerator negated.
+ denominator := denominator negated
+ ]
+ ].
+ (denominator == 1) ifTrue:[^ numerator].
+ ^ self
+!
+
+setNumerator:num denominator:den
+ "set both numerator and denominator"
+
+ numerator := num.
+ denominator := den
+! !
+
+!Fraction methodsFor:'queries'!
+
+isFraction
+ "return true, if the receiver is some kind of fraction;
+ true is returned here - the method is redefined from Object."
+
+ ^ true
+! !
+
+!Fraction methodsFor:'testing'!
+
+negative
+ "return true if the receiver is negative"
+
+ (numerator < 0) ifTrue:[
+ ^ (denominator < 0) not
+ ].
+ ^ (denominator < 0)
+! !
+
+!Fraction methodsFor:'truncation and rounding'!
+
+rounded
+ "return the receiver rounded to the nearest integer as integer"
+
+ self negative ifTrue:[
+ ^ (self + (1/2)) truncated - 1
+ ].
+ ^ (self + (1/2)) truncated
+!
+
+truncated
+ "return the receiver truncated towards zero as Integer"
+
+ ^ numerator // denominator
+! !
+
+!Fraction class methodsFor:'documentation'!
+
+version
+ ^ '$Header: /cvs/stx/stx/libbasic/Fraction.st,v 1.25 1995-12-07 21:34:45 cg Exp $'
+! !
+Fraction initialize!