Skip to content
Discussions/App Development/Write a For Loop in DAMLForum ↗

Write a For Loop in DAML

App Development5 posts1,559 views19 likesLast activity Jan 2021
AR
Arvind_RaoOP
Apr 2020

Hi, Sorry for Newbie question, but how do I write a loop in DAML

eg. In following code, I want to create QuoteRequest’s passing the element from the array quoteInfos for each

...
nonconsuming CreateQuoteRequest : ContractId QuoteRequest
        with 
          quoteInfos : [QuoteInfo]
        do 
-- For (element in quoteInfos)
--  create QuoteRequest with element

...

template QuoteRequest
  with 
    quoteInfo : QuoteInfo
  where 
...

thanks

CO
cocreature
Apr 2020

In DAML, there is no builtin construct that corresponds to a for-loop. However, there is a standard library function for this:

forA : Applicative m => [a] -> (a -> m b) -> m [b]

In your case you can instantiate the type variables to get:

forA : [QuoteInfo] -> (QuoteInfo -> Update (ContractId QuoteRequest)) -> Update [ContractId QuoteRequest]

Using this you can implement your choice as follows:

-- Note that I changed the type to return a list of contract ids. If you
-- only want to return one you have to decide which one and
-- what you want to do if `quoteInfos` is empty.
nonconsuming CreateQuoteRequest : [ContractId QuoteRequest]
  with
    quoteInfos : [QuoteInfo]
  do forA quoteInfos (\quoteInfo -> create QuoteRequest with quoteInfo)

If you do not care about the result, you can also use forA_ (you have to import DA.Foldable for that).

forA_ : [a] -> (a -> f b) -> f ()

Now you might wonder how those library functions are implemented themselves. The answer is recursion! Any for loop can be translated into a recursive function. Let’s take your example above and translate it into a recursive function:

createQuoteRequests : [QuoteInfo] -> Update [ContractId QuoteRequest]
createQuoteRequests [] = pure [] -- no quote infos so nothing to do
createQuoteRequests (quoteInfo :: quoteInfos) = do
  -- at least one quote info, first create that
  quoteRequestId <- create QuoteRequest with quoteInfo
  -- then recursively call createQuoteRequests to handle the tail of the list.
  quoteRequestIds <- createQuoteRequests quoteInfos
  -- now combine the results
  return (quoteRequestId :: quoteRequestIds)

This solves your specific problem. However because certain patterns occur so frequently they are captured as higher order functions in the standard library and it is generally good practice to make use of them instead of writing your own recursive functions.

AR
Arvind_Rao
Apr 2020

Thank you for the Quick response

SH
Shaul
Apr 2020

This can be a worthy addition to @drsk’s DAML cheat sheet

IQ
Iqra_Mustafa
Jan 2021

https://docs.daml.com/cheat-sheet/

← Back to Discussions