Re: 答复 : [Haskell-cafe] How to do this in FP way?
magicloud.magiclouds: OK. Here it is. I want to make a monitor tool for linux. It runs for a long time, and give out a certain process's io stat per second. The way I get io stat is to read from /proc/pid/io. But the data in this file is a total, I need to read it first, then next second, read it again, and shows the difference, and go on. So, what is your idea? Easy, import Control.Concurrent import Control.Monad main = go 0 where go st = forever $ do n - read `fmap` readFile /proc/pid/io print (n - st) -- display difference threadDelay (10^6) -- Don ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: 答复 : [Haskell-cafe] How to do this in FP way?
dons: magicloud.magiclouds: OK. Here it is. I want to make a monitor tool for linux. It runs for a long time, and give out a certain process's io stat per second. The way I get io stat is to read from /proc/pid/io. But the data in this file is a total, I need to read it first, then next second, read it again, and shows the difference, and go on. So, what is your idea? Easy, import Control.Concurrent import Control.Monad main = go 0 where go st = forever $ do n - read `fmap` readFile /proc/pid/io print (n - st) -- display difference threadDelay (10^6) Oops, not 'forever' :) go st = do ... go n ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: 答复 : [Haskell-cafe] How to do this in FP way?
On Tue, Jun 17, 2008 at 08:56:31AM -0700, Don Stewart wrote: dons: magicloud.magiclouds: OK. Here it is. I want to make a monitor tool for linux. It runs for a long time, and give out a certain process's io stat per second. The way I get io stat is to read from /proc/pid/io. But the data in this file is a total, I need to read it first, then next second, read it again, and shows the difference, and go on. So, what is your idea? Easy, import Control.Concurrent import Control.Monad main = go 0 where go st = forever $ do n - read `fmap` readFile /proc/pid/io print (n - st) -- display difference threadDelay (10^6) Oops, not 'forever' :) go st = do ... go n or doEverySecond :: (a - IO a) - a - IO () doEverySecond job n = do n' - job n threadDelay (10^6) doEverySecond job n' showChange :: Int - IO Int showChange n = do n' - read `fmap` readFile /proc/pid/io print (n' - n) -- display difference return n' main = doEverySecond showChange 0 -- note: prints bogus value first time This demonstrates how you can abstract the ideas in Don's solution just a bit, so that you could reuse these functions for somewhat different purposes. For such a simple function you'd probably be better with Don's solution, but if your monitor tool is starting to look more complicated than this, perhaps you're better off breaking it into different functions. David ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] How to do this in FP way?
Magicloud Magiclouds [EMAIL PROTECTED] writes: static int old; int diff (int now) { /* this would be called once a second */ int ret = now - old; old = now; return ret; } Because there is no variable in Haskell. So how to do this in a FP way? I would claim the FP way is like this: -- | Repeatedly subtract values from a baseline, returning a list -- containing each intermediate result diff :: Int - [Int] - [Int] diff = scanl (-) Prelude diff 100 [1..10] [100,99,97,94,90,85,79,72,64,55,45] -k -- If I haven't seen further, it is by standing in the footprints of giants ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] How to do this in FP way?
On Mon, 2008-06-16 at 10:19 +0200, Ketil Malde wrote: Magicloud Magiclouds [EMAIL PROTECTED] writes: static int old; int diff (int now) { /* this would be called once a second */ int ret = now - old; old = now; return ret; } Because there is no variable in Haskell. So how to do this in a FP way? I would claim the FP way is like this: -- | Repeatedly subtract values from a baseline, returning a list -- containing each intermediate result diff :: Int - [Int] - [Int] diff = scanl (-) Prelude diff 100 [1..10] [100,99,97,94,90,85,79,72,64,55,45] Better yet, you could create a recursive type that reflects what you are actually doing: newtype Step a = Step (a - (a, Step a)) diff' :: Int - Step Int diff' x = Step (\a - let r = a - x in (r, diff' r)) This way it will be easier to resume previous diff computations. Best, Michał ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] How to do this in FP way?
2008/6/15 Magicloud Magiclouds [EMAIL PROTECTED]: Hello, I am getting familiar with FP now, and I have a program design kind of question. Say I have something like this in C: static int old; int diff (int now) { /* this would be called once a second */ int ret = now - old; old = now; return ret; } Because there is no variable in Haskell. So how to do this in a FP way? A better question would be to think about what you are trying to accomplish, and then ask how to achieve that through functional programming. David ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] How to do this in FP way?
On Mon, Jun 16, 2008 at 10:31:22AM +0800, Magicloud Magiclouds wrote: Hello, I am getting familiar with FP now, and I have a program design kind of question. Say I have something like this in C: static int old; int diff (int now) { /* this would be called once a second */ int ret = now - old; old = now; return ret; } Because there is no variable in Haskell. So how to do this in a FP way? Thanks. I think that called once a second suggests that you perhaps should not do that in a FP way. A state-changing function called frequently suggests that you are perhaps doing something with a notion of time, maybe a game? Then FRP is your FP approach. Or I would recommend you to explain your problem, because FP approach could lie on much more higher level than one can figure out looking at your short snippet. ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe -- pierre ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] How to do this in FP way?
On 6/16/08, Magicloud Magiclouds [EMAIL PROTECTED] wrote: Hello, I am getting familiar with FP now, and I have a program design kind of question. Say I have something like this in C: static int old; int diff (int now) { /* this would be called once a second */ int ret = now - old; old = now; return ret; } Because there is no variable in Haskell. So how to do this in a FP way? The short answer is that your question amounts to How do I do imperative programming in an FP way, to which the answer is you really should try to avoid it. Longer answer: I think you'll be bette served if you describe your problem on a much higher level than this. Chances are that if you write your program in an FP way, you wouldn't need a function like your diff. That said, Haskell do have variables (in this case an IORef would do what you want), but again, you probably don't want that, so if you post what problem you're trying to solve using diff, then it will be easier to help you design it in an FP way. Doing things in an FP way tend to impact your program a lot more than just some minor changes to the functions at the bottom, it will change the whole design. -- Sebastian Sylvan +44(0)7857-300802 UIN: 44640862 ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] How to do this in FP way?
David Roundy wrote: A better question would be to think about what you are trying to accomplish, and then ask how to achieve that through functional programming. Amen! I was waiting for somebody to say that... There are a dozen situations in an imperative language where you'd write a loop. But in Haskell, you might well do something entirely different for each situation. So it really pays to focus on what the end result you're after is, rather than how to translate imperative code line-for-line into Haskell. ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
[Haskell-cafe] How to do this in FP way?
Hello, I am getting familiar with FP now, and I have a program design kind of question. Say I have something like this in C: static int old; int diff (int now) { /* this would be called once a second */ int ret = now - old; old = now; return ret; } Because there is no variable in Haskell. So how to do this in a FP way? Thanks. ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] How to do this in FP way?
Magicloud Magiclouds wrote: Say I have something like this in C: static int old; int diff (int now) { /* this would be called once a second */ int ret = now - old; old = now; return ret; } Because there is no variable in Haskell. So how to do this in a FP way? So you have a global time count that is updated every second - I presume for the rest of the process to use, avoiding syscalls due to expense. Am I getting this right? You can use mutable variables in Haskell, though some people will frown, but it might fit your need. See MVar, STM, or IO Refs. At any rate, if what you are doing needs to check the clock time then this code isn't going to be pure. Perhaps you just want something in particular to be triggered every second then use control-timeout, event-list, or control-event. Tom signature.asc Description: This is a digitally signed message part ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] How to do this in FP way?
I can think of 2 ways. module Main where import Control.Monad.State First, normal way: diff (now, old) = (now - old, now) diff takes now and old and returns result (now - old) and modified old (now). For example, diff (diff (1,0)) == diff (1 - 0, 1) == diff (1, 1) == (1 - 1, 1) == (0, 1) I think people use the word threaded to describe what diff is doing: the variable old is threaded through many calls to diff. testDiff = diff . diff . diff . diff . diff . diff $ (2, 1) testDiff returns (2,1) Second way is using monads: diff' now = do old - get put now return (now - old) diff' uses State monad. If you're not familiar with monads, State monad does similar to what diff function does (it threads the variable old). But, being a monadic action, diff' looks like imperative version syntactically. It gives illusion of having global variable (old). testDiff' = do result - diff' 2 result - diff' result result - diff' result result - diff' result result - diff' result result - diff' result return result runTestDiff' = runState testDiff' 1 runTestDiff' also returns (2,1) 2008/6/15 Magicloud Magiclouds [EMAIL PROTECTED]: Hello, I am getting familiar with FP now, and I have a program design kind of question. Say I have something like this in C: static int old; int diff (int now) { /* this would be called once a second */ int ret = now - old; old = now; return ret; } Because there is no variable in Haskell. So how to do this in a FP way? Thanks. ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe