call a foreign program to do work in your current program in scheme

60 Views Asked by At

I was wondering if you're allowed to call another program you made to do work in a new program you are about to make in scheme, or would I have to copy and paste all the code from the previous program, though I can do this and make my life simple, I'm wondering if there is a more sophisticated elegant way to import in scheme r5rs.

;; Here is an example of what I mean
;; for example I have a file name add.scm which adds 2 numbers
;; now I want to make a new function that squares the numbers
;;is there a way I can do something like this
#lang add.scm as add

;;and use it here like so
(define (square x)
  (* x x))
(square add)
;;where add already returns a value

This may seem like a silly piece of code, but this is the best pesudo code I can give, if the example needs more editing to understand please let me know, thank you.

2

There are 2 best solutions below

0
Ryan Culpepper On

If I understand your question, you have this module named add.scm:

;; add.scm
#lang racket
(+ 5 7) ;; prints 12 when run

and you want to write a new module that gets the value that the add.scm module prints out, bind it to a variable, and use it in a computation, like this:

;; square.scm
#lang racket
(??? add ??? "add.scm" ???) ;; bind `add` to "value" of "add.scm" module
(* add add) ;; prints 144 when run

No, there is no easy way to do that. It's possible, by using dynamic-require or a subprocess to run the module, capturing the output and then reading it to get the value, but that's an awful, complicated, brittle way to do things.

In Racket, a better approach would be for add.rkt to define and export a variable and have a main submodule that prints the value:

;; add.rkt
#lang racket
(provide x)
(define x (+ 5 7))
(module+ main
  x)

Then you can use (require "add.rkt") from another module to get x to use in computations, and if you run add.rkt as a program (for example, with racket add.rkt), then it prints the value.

0
mnemenaut On

Racket (which has #lang as in the question, and module/provide/require as explained in another answer) is not Scheme (let alone R5RS).

In R6RS Scheme, Scheme source can be divided between library files and top-level programs

If the file add-library.scm contains:

(library (add-library)
  (export add)
  (import (rnrs))
  
  (define add (+ 5 7)) )

and add-toplevel.scm contains:

(import (add-library))

(define (square x)
  (* x x))
  
(display (square add))

Then:

$ scheme

> (load "add-toplevel.scm")
144
>