Reputation: 13
I am trying to figure out how I can recursively define a function while also calling a second function at one of the original integer max values. I don't want to add another integer input however I want to call the second function with the integer from the first function (but only once) I would happily also shorten this down into 1 function if that's better/possible
testFunction::Int->String
testFunction s
|s == 0 = ""
|otherwise = "abc" ++ testFunction (s-1) ++ testFunction2 s
testFunction2::Int->String
testFunction2 s
|s == 0 = ""
|otherwise = testFunction2 (s-1)++"cba"
For example, this will call testFunction recursively and then because it does this it will call testFunction2 multiple times with s-1 in the main function. I only want the content of testFunction2 to be called once and only with the initial value of S without adding any other int inputs. Say I called 'testFunction 2' it currently outputs 'abcabccbacbacba', however I only want cba outputted twice so I really want 'abcabccbacba' Thank you for the help :)
Upvotes: 1
Views: 350
Reputation: 71109
Your function looks like an equivalent of
testFunction s = concat (replicate s "abc") ++
concat (replicate (s*(s+1)`div`2) "cba")
and you apparently want
testFunction s = concat (replicate s "abc") ++
concat (replicate s "cba")
So, there it is, shortened down into one function. But it's not recursive (it's not clear to me if that's a hard requirement here, or not).
It could also be written
= concat (replicate s "abc" ++ replicate s "cba")
= concat $ concatMap (replicate s) ["abc", "cba"]
= ["abc", "cba"] >>= replicate s >>= id
Upvotes: 1
Reputation: 51029
The usual way of doing this sort of thing is to break the function up into some non-recursive "top-level" processing and a recursive helper, usually defined in a where
clause and given a generic name like go
or step
or loop
.
So, you might write:
testFunction :: Int -> String
testFunction s
| s == 0 = ""
| otherwise
-- here's the top-level processing
= "abc" ++ go (s-1) ++ testFunction2 s
where
-- here's the recursive helper
go s | s == 0 = ""
| otherwise = "abc" ++ go (s-1)
In this example, this results in some repeated code. You can refactor to remove some of the duplication, though it may be difficult to remove all of it (e.g., the s == 0
handling):
testFunction :: Int -> String
testFunction s
| s == 0 = ""
| otherwise = go s ++ testFunction2 s
where
go s | s == 0 = ""
| otherwise = "abc" ++ go (s-1)
Upvotes: 2