-
Notifications
You must be signed in to change notification settings - Fork 52
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #596 from Inao0/master
Add Venn Diagram for two sets
- Loading branch information
Showing
2 changed files
with
191 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,133 @@ | ||
" | ||
This class creates a Venn Diagram to visualise two sets of data and their intersection. | ||
This does not work for more than two sets for now. | ||
The formula used to compute it are available at: https://dspace.library.uvic.ca/bitstream/handle/1828/128/phdGradStudiesMay24.pdf | ||
" | ||
Class { | ||
#name : #RSCircleVennDiagram, | ||
#superclass : #RSBuilder, | ||
#instVars : [ | ||
'bigSet', | ||
'smallSet', | ||
'omega', | ||
'treshold' | ||
], | ||
#category : #'Roassal3-Builders-VennDiagram' | ||
} | ||
|
||
{ #category : #examples } | ||
RSCircleVennDiagram class >> example1 [ | ||
|
||
^ self new | ||
bigSet: { 1. 2. 3. 4. 5. 6. 8. 9. 0. 0. 8 }; | ||
smallSet: { 1. 2. 10. 20. 50. 14 }; | ||
open | ||
] | ||
|
||
{ #category : #accessing } | ||
RSCircleVennDiagram >> bigSet [ | ||
|
||
^ bigSet | ||
] | ||
|
||
{ #category : #accessing } | ||
RSCircleVennDiagram >> bigSet: anObject [ | ||
|
||
bigSet := anObject asSet. | ||
] | ||
|
||
{ #category : #computation } | ||
RSCircleVennDiagram >> computeDistance [ | ||
|
||
| bigRadius smallRadius intersection intersectionWeight lowBoundary highBoundary deltaFunction middle | | ||
bigRadius := self computeRadius: bigSet. | ||
smallRadius := self computeRadius: smallSet. | ||
intersection := bigSet intersection: smallSet. | ||
intersectionWeight := self weight: intersection. | ||
|
||
lowBoundary := bigRadius - smallRadius. | ||
highBoundary := bigRadius + smallRadius. | ||
deltaFunction := [ :d | | ||
| alpha beta delta | | ||
alpha := 2 | ||
* | ||
(d squared + bigRadius squared | ||
- smallRadius squared / 2 * bigRadius * d) | ||
arcCos. | ||
beta := 2 | ||
* | ||
(d squared - bigRadius squared | ||
+ smallRadius squared / 2 * smallRadius | ||
* d) arcCos. | ||
delta := 0.5 * bigRadius squared | ||
* (alpha - alpha) sin | ||
+ | ||
(0.5 * smallRadius squared | ||
* (beta - beta sin)). | ||
delta ]. | ||
|
||
"Bisection algorithm" | ||
middle := lowBoundary + highBoundary / 2. | ||
[ (deltaFunction value: middle) - intersectionWeight < treshold ] | ||
whileFalse: [ | ||
(deltaFunction value: middle) > intersectionWeight | ||
ifTrue: [ lowBoundary := middle ] | ||
ifFalse: [ highBoundary := middle ]. | ||
middle := lowBoundary + highBoundary / 2 ]. | ||
^ middle | ||
] | ||
|
||
{ #category : #accessing } | ||
RSCircleVennDiagram >> computeRadius: aSet [ | ||
|
||
^ ((self weight: aSet) / Float pi) sqrt | ||
] | ||
|
||
{ #category : #initialization } | ||
RSCircleVennDiagram >> initialize [ | ||
super initialize. | ||
bigSet := Set new. | ||
smallSet := Set new. | ||
treshold := 0.001. "Accuracy of intersection area" | ||
] | ||
|
||
{ #category : #rendering } | ||
RSCircleVennDiagram >> renderIn: aCanvas [ | ||
|
||
| bigRadius smallRadius distance | | ||
(bigSet isEmpty or: [ smallSet isEmpty ]) ifTrue: [ ^ self ]. | ||
|
||
omega := bigSet asSet. | ||
omega addAll: smallSet. | ||
bigRadius := self computeRadius: bigSet. | ||
smallRadius := self computeRadius: smallSet. | ||
distance := self computeDistance. | ||
|
||
aCanvas newCircle | ||
radius: bigRadius * 10; | ||
color: Color blue translucent; | ||
position: 0 asPoint. | ||
aCanvas newCircle | ||
radius: smallRadius * 10; | ||
position: distance * 10 @ 0; | ||
color: Color red translucent. | ||
aCanvas @ RSCanvasController. | ||
] | ||
|
||
{ #category : #accessing } | ||
RSCircleVennDiagram >> smallSet [ | ||
|
||
^ smallSet | ||
] | ||
|
||
{ #category : #accessing } | ||
RSCircleVennDiagram >> smallSet: anObject [ | ||
|
||
smallSet := anObject asSet. | ||
] | ||
|
||
{ #category : #accessing } | ||
RSCircleVennDiagram >> weight: aSet [ | ||
|
||
^ aSet size / omega size | ||
] |
58 changes: 58 additions & 0 deletions
58
src/Roassal3-Global-Tests/RSCircleVennDiagramTest.class.st
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,58 @@ | ||
Class { | ||
#name : #RSCircleVennDiagramTest, | ||
#superclass : #RSTest, | ||
#instVars : [ | ||
'vennDiagram' | ||
], | ||
#category : #'Roassal3-Global-Tests-Builder' | ||
} | ||
|
||
{ #category : #running } | ||
RSCircleVennDiagramTest >> setUp [ | ||
super setUp. | ||
|
||
vennDiagram := RSCircleVennDiagram new. | ||
] | ||
|
||
{ #category : #tests } | ||
RSCircleVennDiagramTest >> testBasicVennDiagramOpen [ | ||
|
||
| window | | ||
window := vennDiagram open. | ||
window delete | ||
] | ||
|
||
{ #category : #tests } | ||
RSCircleVennDiagramTest >> testVennDiagramConvertsBigSetInputToSet [ | ||
|
||
vennDiagram bigSet: { 1 . 2 }. | ||
self assert: vennDiagram bigSet class equals: Set. | ||
|
||
] | ||
|
||
{ #category : #tests } | ||
RSCircleVennDiagramTest >> testVennDiagramConvertsSmallSetInputToSet [ | ||
|
||
vennDiagram smallSet: { 1 . 2 }. | ||
self assert: vennDiagram smallSet class equals: Set. | ||
|
||
] | ||
|
||
{ #category : #tests } | ||
RSCircleVennDiagramTest >> testVennDiagramOneSet [ | ||
|
||
vennDiagram bigSet: { 3 . 2 }. | ||
vennDiagram build. | ||
self assert: vennDiagram canvas shapes size equals: 0. | ||
|
||
] | ||
|
||
{ #category : #tests } | ||
RSCircleVennDiagramTest >> testVennDiagramTwoSets [ | ||
|
||
vennDiagram bigSet: { 3 . 2 }. | ||
vennDiagram smallSet: { 1. 3 . 2 }. | ||
vennDiagram build. | ||
self assert: vennDiagram canvas shapes size equals: 2. | ||
|
||
] |