[racket] fuzzy set representation in Racket

From: Matthias Felleisen (matthias at ccs.neu.edu)
Date: Fri Aug 23 20:02:30 EDT 2013

Here is one more alternative: 

#lang racket

;; you can move the body of this module into a '#lang racket' file called fuzzy-set-library.rkt 
(module fuzzy-set-library racket 
  ;; rename-out is an elegant version of the let()/define-values trick in Realm of Racket 
  (provide (rename-out (fuzzy-set0 fuzzy-set)) (struct-out fuzzy-element))
  (struct fuzzy-element (val degree) #:transparent)
  ;; FE = (fuzzy-element Any [0,1))
  (struct fuzzy-set (vals) 
    ;; [List-of FE] -> Fuzzy-set
    (lambda (le type-name)
      (define-values (members _)
        (for/fold ((s '()) (keys '())) ((x le))
          (unless (fuzzy-element? x) 
            (error type-name "fuzzy-element expected, given: ~e" x))
          (define k (fuzzy-element-val x))
          (if (member k keys)
              (values s keys)
              (values (cons x s) (cons k keys)))))
      (apply set members)))
  ;; FuzzySet = (fuzzy-set [Set-of FE])
  (define (fuzzy-set0 . x) ;; <--- this means take as many arguments as there are, as a list 
    (fuzzy-set x))
  ;; add
  ;; -- fuzzy-add-element 
  ;; -- fuzzy-union 
  ;; etc.

;; this could be a '#lang racket' file too
(module fuzzy-set-client racket 
  ;; then you replace this with the usual require 
  (require (submod ".." fuzzy-set-library))

   (fuzzy-element 'a .1)
   (fuzzy-element 'b .2)
   (fuzzy-element 'c .3)
   (fuzzy-element 'a .3)))

;; drop this, it exists to test 
(require 'fuzzy-set-client)

On Aug 23, 2013, at 3:49 PM, Rian Shams wrote:

> Hello All,
> My name is Rian and I am a new Racket user and a novice programmer (Racket is my first language). First let me say that I am very grateful for the resources available online and the books, HTDP and Realm of Racket. I find your teaching methods very clear and as a result I am picking up Racket faster than I originally thought.
> I am a System Science graduate student whose primary research focus is on Fuzzy Set Theory. A fuzzy set is a collection of distinct elements where each element has a degree of membership associated with it. 
> The representation I am currently using for a fuzzy set is the following:
> First I create a struct called fuzzy-element which consists of 2 fields; the first is the name of the element and the second is the elements degree of membership to the set which ranges from 0 to 1.
> ;; Data Definition
> #lang racket
> (struct fuzzy-element (member degree-of-membership) 
>   #:transparent
>   #:guard (lambda (member degree-of-membership type-name)
>             (cond
>               [(not (and (number? degree-of-membership)
>                          (<= 0 degree-of-membership 1) degree-of-membership))
>                (error type-name
>                       "~e is not a number between 0 and 1"
>                       degree-of-membership)]
>               [else (values member degree-of-membership)])))
> ;; fuzzy-element is (fuzzy-element Symbol Number[0, 1])
> ;; interp. a fuzzy-element as a struct in which:
> ;;         -the first field is the member's name
> ;;         -the second field is the respective members degree of membership
> Then I combine them with a list so what I have now is a list of fuzzy elements.
> ;; ListOfFuzzyElement is one of:
> ;; - empty
> ;; - (cons fuzzy-element ListOfFuzzyElement)
> The problem with this data definition is that it allows for duplicate structs with the same field-1 elements.
> What I am looking to create is
> ;; A Fuzzy-Set is one of:
> ;; - empty list
> ;; - (cons distinct fuzzy-element ListOfFuzzyElement)
> Ideally the type of representation I would like to use should look like: 
> (fuzzy-set (fuzzy-element 'a .1)
>                (fuzzy-element 'b .2)
>                (fuzzy-element 'c .3)
>                (fuzzy-element 'a .3))
> -> (fuzzy-set (fuzzy-element 'a .1)
>                    (fuzzy-element 'b .2)
>                    (fuzzy-element 'c .3))
> Upon evaluation, the last element, (fuzzy-element 'a .3) is deleted because there already exists a member named 'a (fuzzy-element 'a .1). It should work exactly like the built in "set" data type, except in this case it is a set of structures that checks the first fields of all structures and eliminates latter duplicates. 
> Any guidance on how to create fuzzy-set representation this way or if you can suggest more concise and elegant methods I would be greatly appreciative. 
> Thanks,
> -- 
> Rian Shams
> ____________________
>  Racket Users list:
>  http://lists.racket-lang.org/users

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.racket-lang.org/users/archive/attachments/20130823/c008e71d/attachment-0001.html>

Posted on the users mailing list.