简体   繁体   中英

Parse through list in Scheme and get the sum of all the numbers

So I need to write a recursive solution that can go through the directory and subdirectory of a list and add up the file sizes. I have zero experience in scheme and my professor isn't getting back to me. I've tried a few different attempts but they all end in errors. If anyone could help me out it'd be greatly appreciated because I don't have much time left to figure out this assignment.

(define disk '("D" "main"
(
    ("F" "file1.txt" (30))
    ("F" "file2.txt" (11))

    ("D" "sub1"
    (
        ( "F" "file1.txt" (1234))
        ( "F" "file2.txt" (2345))
        ( "F" "file3.txt" (3456))
    )
    )
    ("D" "sub2"
    (
        ( "F" "file1.txt" (1234))
        ( "F" "file2.txt" (2345))
        ( "F" "file3.txt" (3456))
    )
    )
)
)
)

(define (getEnd n)
    (let ((n 1)))
    (let ((m 0)))
    (member 3 '(disk.n))
    (+ m (getEnd (+ n 1)))

)

When I run the code I always get this error:

          Ill-formed special form: (let (...))

I've tried using the let statement outside of the function but it still doesn't work because I have no clue how scheme works. I've reached out to my classmates and they can't seem to figure it out either.

Any help would be appreciated, thank you!

A let is a local bound variable that exist during the body or the form. That is:

(let ((n 1))           ; bind one variable 1
  (display (+ n n))    ; use n for something
  )                    ; end of let. `n` no longer exist.

Since you have tag java, C dialect, it's the same as this:

{
  int n = 1;
  System.out.println(n + n); // use n for something
}
// end of block. n no longer exist

In your code you have no expressions using the binding and if it was allowed it would have been dead code, like this:

{
  int n = 1;
}
// end of block. n no longer exist

The code (member 3 '(disk.n)) is always #f since '(disk.n) is a list with one symbol, disk.n and (equal? 3 'disk.n) ; ==> #f (equal? 3 'disk.n) ; ==> #f

The last line (+ m (getEnd (+ n 1)) does an unconditional recursion by increasing n . It does not sum any numeric values from the structure.

questions

It seems you can check if a list is a file or directory by looking at the first element is either "F" or "D" Thus you could make:

(define (file? lst)
  ; todo: implement
  )

(file? '("F" "file1.txt" (1234))) ; ==> #t
(file? '("D" ())                  ; ==> #f

You can get a list of files by checking the third element of a directory:

(define (directory-elements dir)
  ; todo: implement
  )

(directory-elements '("D" "D" (("F" "F1" (1234)) ("F" "F2" (2345)))))
; ==> (("F" "F1" (1234)) ("F" "F2" (2345)))

You can make a procedure that gets the size of a file:

(define (file-size file)
  ; todo: implement
  )

(file-size '("F" "F1" (1234)))
; ==> 1234

Now you can make your target procedure using the ones above:

(define (size file-or-dir)
  (if (file? file-or-dir)
      (file-size file-or-dir)
      (directory-elements-size (directory-elements file-or-dir)))

(size '("F" "F1" (1234))) ; ==> 1234
(size '("D" "D" (("F" "F1" (1234)) ("F" "F2" (2345))))) ; ==> 3579

You are missing directory-elements-size . That can be made with recursion:

(define (directory-elements-size lst)
  (if (null? lst)
      <???>                                  ; size of an empty directory
      (+ (size <????>)                       ; add the size of first file/dir
         (directory-elements-size <????>)))) ; with the size of the rest of the elements

There you go. You should have more than enough to get you going.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM