|
|
|
|
|
|
| Author |
Message |
Keith Thompson *nix forums Guru
Joined: 28 Feb 2005
Posts: 5173
|
Posted: Thu Jul 20, 2006 3:17 pm Post subject:
Re: Function Wrapper: Opinions and Critique Desired
|
|
|
jaysome <jaysome@spamcop.net> writes:
| Quote: | On Thu, 20 Jul 2006 06:29:49 +0000 (UTC), "I.M. !Knuth"
not_knuth@yoyodyne.com> wrote:
[...]
BTW, what's the "as-if rule"?
The intention was to provide direction through example. The examples
were meant to be unambiguous. I think the committee achieved that for
the most part.
|
Um, what does that have to with the "as-if" rule?
--
Keith Thompson (The_Other_Keith) kst-u@mib.org <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <*> <http://users.sdsc.edu/~kst>
We must do something. This is something. Therefore, we must do this. |
|
| Back to top |
|
 |
jaysome *nix forums addict
Joined: 01 Mar 2006
Posts: 69
|
Posted: Thu Jul 20, 2006 8:51 am Post subject:
Re: Function Wrapper: Opinions and Critique Desired
|
|
|
On Thu, 20 Jul 2006 06:29:49 +0000 (UTC), "I.M. !Knuth"
<not_knuth@yoyodyne.com> wrote:
| Quote: | Keith Thompson <kst-u@mib.org> wrote:
Barry Schwarz <schwarzb@doezl.net> writes:
On Wed, 19 Jul 2006 06:33:14 +0000 (UTC), "I.M. !Knuth"
not_knuth@yoyodyne.com> wrote:
snip
--> static int prev_pos; /* conveniently init'd to 0 on 1st call */
Just a nit. Static variables are initialized prior to your program
beginning execution and independent of your function.
True -- but, by the as-if rule, an implementation conceivably *could*
delay the initialization until the first call. (Nothing outside the
function can see the variable before that and detect that it hasn't
been initialized. Local static variables can be seen via pointers
outside the function that defines them, but there's no way to
initialize such a pointer before calling the function.)
But I can't think of a good reason for an implementation to do such a
silly thing.
So, hypothetically, I only look dumb under some implementation-specific
circumstances. :-D
BTW, what's the "as-if rule"?
|
The intention was to provide direction through example. The examples
were meant to be unambiguous. I think the committee achieved that for
the most part.
Best regards
--
jay |
|
| Back to top |
|
 |
Keith Thompson *nix forums Guru
Joined: 28 Feb 2005
Posts: 5173
|
Posted: Thu Jul 20, 2006 8:00 am Post subject:
Re: Function Wrapper: Opinions and Critique Desired
|
|
|
"I.M. !Knuth" <not_knuth@yoyodyne.com> writes:
| Quote: | Keith Thompson <kst-u@mib.org> wrote:
Barry Schwarz <schwarzb@doezl.net> writes:
On Wed, 19 Jul 2006 06:33:14 +0000 (UTC), "I.M. !Knuth"
not_knuth@yoyodyne.com> wrote:
snip
--> static int prev_pos; /* conveniently init'd to 0 on 1st call */
Just a nit. Static variables are initialized prior to your program
beginning execution and independent of your function.
True -- but, by the as-if rule, an implementation conceivably *could*
delay the initialization until the first call. (Nothing outside the
function can see the variable before that and detect that it hasn't
been initialized. Local static variables can be seen via pointers
outside the function that defines them, but there's no way to
initialize such a pointer before calling the function.)
But I can't think of a good reason for an implementation to do such a
silly thing.
So, hypothetically, I only look dumb under some implementation-specific
circumstances.
|
Um, sure. }
| Quote: | BTW, what's the "as-if rule"?
|
The general idea is that the standard describes the behavior of an
abstract machine, but the actual generated code is allowed to behave
differently as long as the result is *as if* it followed the semantics
described in the standard. It allows for optimizations such as
eliminating calculations whose results are never used.
C99 5.1.2.2.3p3:
In the abstract machine, all expressions are evaluated as
specified by the semantics. An actual implementation need not
evaluate part of an expression if it can deduce that its value is
not used and that no needed side effects are produced (including
any caused by calling a function or accessing a volatile object).
C99 5.1.2.2.3p5:
The least requirements on a conforming implementation are:
-- At sequence points, volatile objects are stable in the sense
that previous accesses are complete and subsequent accesses
have not yet occurred.
-- At program termination, all data written into files shall be
identical to the result that execution of the program according
to the abstract semantics would have produced.
-- The input and output dynamics of interactive devices shall take
place as specified in 7.19.3. The intent of these requirements
is that unbuffered or line-buffered output appear as soon as
possible, to ensure that prompting messages actually appear
prior to a program waiting for input.
--
Keith Thompson (The_Other_Keith) kst-u@mib.org <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <*> <http://users.sdsc.edu/~kst>
We must do something. This is something. Therefore, we must do this. |
|
| Back to top |
|
 |
I.M. !Knuth *nix forums beginner
Joined: 26 Jun 2006
Posts: 14
|
Posted: Thu Jul 20, 2006 6:29 am Post subject:
Re: Function Wrapper: Opinions and Critique Desired
|
|
|
Keith Thompson <kst-u@mib.org> wrote:
| Quote: | Barry Schwarz <schwarzb@doezl.net> writes:
On Wed, 19 Jul 2006 06:33:14 +0000 (UTC), "I.M. !Knuth"
not_knuth@yoyodyne.com> wrote:
snip
--> static int prev_pos; /* conveniently init'd to 0 on 1st call */
Just a nit. Static variables are initialized prior to your program
beginning execution and independent of your function.
True -- but, by the as-if rule, an implementation conceivably *could*
delay the initialization until the first call. (Nothing outside the
function can see the variable before that and detect that it hasn't
been initialized. Local static variables can be seen via pointers
outside the function that defines them, but there's no way to
initialize such a pointer before calling the function.)
But I can't think of a good reason for an implementation to do such a
silly thing.
|
So, hypothetically, I only look dumb under some implementation-specific
circumstances.
BTW, what's the "as-if rule"?
--
I.M. (definitely) !Knuth |
|
| Back to top |
|
 |
I.M. !Knuth *nix forums beginner
Joined: 26 Jun 2006
Posts: 14
|
Posted: Thu Jul 20, 2006 6:21 am Post subject:
Re: Function Wrapper: Opinions and Critique Desired
|
|
|
Barry Schwarz <schwarzb@doezl.net> wrote:
| Quote: | On Wed, 19 Jul 2006 06:33:14 +0000 (UTC), "I.M. !Knuth"
not_knuth@yoyodyne.com> wrote:
snip
--> static int prev_pos; /* conveniently init'd to 0 on 1st call */
Just a nit. Static variables are initialized prior to your program
beginning execution and independent of your function.
|
D'oh! I knew that. Really, I did.
--
I.M. (definitely) !Knuth |
|
| Back to top |
|
 |
I.M. !Knuth *nix forums beginner
Joined: 26 Jun 2006
Posts: 14
|
Posted: Thu Jul 20, 2006 6:18 am Post subject:
Re: Function Wrapper: Opinions and Critique Desired
|
|
|
Morris Dovey <mrdovey@iedu.com> wrote:
<snip>
| Quote: | I have two short pieces of recursive code that you might find
interesting:
http://www.iedu.com/mrd/c/getsm.c and
http://www.iedu.com/mrd/c/getsmx.c that deal with a similar situation.
The two are functionally equivalent; but the second module "cheats" in
that it uses a gcc extension to allow embedding one function
declaration inside another. It's non-standard but may have some value
as a thought-provoking device.
|
My, what large comment blocks you have. :-D
I found a number of (even trivial) things thought-provoking. The
imbedded function (getsmx.c) is outright trippy; it would have taken me
a while just to find it without your comments marking its start and end,
and even more time to figure out was going on.
Where you comment like this:
#include <stdio.h> /* fgetc() */
I've been commenting in the reverse:
fgetc(foo); /* <stdio.h> */
I haven't yet noodled much with structures, nor braved malloc at all, so
I'm a bit lost on how you entirely eliminated...
typedef struct {...} getstr; /* getsm.c */
....from getsmx.c. Though I can see where the structure's contents moved
to. I'll take another look after I get some sleep...
Why have some local variables been explicitly declared with automatic
storage duration?
Having an #ifdef encapsulated "in-line" test main() is frickin' cool. I'll
have to borrow this idea. ;-)
I note you use **argv as a parameter to main() instead of the conventional
*argv[]. I like that. The latter confused and frightened me when I was
first learning pointers. Even now, the former seems clearer to me.
I note also that you don't make use at all of argc. This made me laugh. I
recently finished a program that made extensive use of **argv, but I
couldn't find a use for argc. Everytime I re-compiled it I got the
message:
Warning: 'argc' initialized but never used.
....or some such. I contemplated putting in some dummy code just to make
the warning go away. Does gcc not spit out a similar warning?
Thank you most kindly for letting me peek inside your code.
--
I.M. (definitely) !Knuth |
|
| Back to top |
|
 |
Keith Thompson *nix forums Guru
Joined: 28 Feb 2005
Posts: 5173
|
Posted: Thu Jul 20, 2006 2:10 am Post subject:
Re: Function Wrapper: Opinions and Critique Desired
|
|
|
Barry Schwarz <schwarzb@doezl.net> writes:
| Quote: | On Wed, 19 Jul 2006 06:33:14 +0000 (UTC), "I.M. !Knuth"
not_knuth@yoyodyne.com> wrote:
[...]
So I changed it to:
int func_recurs(int arg1, int arg2)
{
--> static int prev_pos; /* conveniently init'd to 0 on 1st call */
Just a nit. Static variables are initialized prior to your program
beginning execution and independent of your function.
|
True -- but, by the as-if rule, an implementation conceivably *could*
delay the initialization until the first call. (Nothing outside the
function can see the variable before that and detect that it hasn't
been initialized. Local static variables can be seen via pointers
outside the function that defines them, but there's no way to
initialize such a pointer before calling the function.)
But I can't think of a good reason for an implementation to do such a
silly thing.
--
Keith Thompson (The_Other_Keith) kst-u@mib.org <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <*> <http://users.sdsc.edu/~kst>
We must do something. This is something. Therefore, we must do this. |
|
| Back to top |
|
 |
Barry Schwarz *nix forums Guru
Joined: 09 Apr 2005
Posts: 390
|
Posted: Thu Jul 20, 2006 1:42 am Post subject:
Re: Function Wrapper: Opinions and Critique Desired
|
|
|
On Wed, 19 Jul 2006 06:33:14 +0000 (UTC), "I.M. !Knuth"
<not_knuth@yoyodyne.com> wrote:
| Quote: | A while back, I was mucking around with a recursive function. For
brevity's sake, I'll define it like this:
int func_recurs(int arg1, int arg2, int prev_pos)
{
int crnt_pos = 0;
int result;
/* stuff happens to arg1, arg2, and crnt_pos */
func_recurs(arg1, arg2, (prev_pos + crnt_pos) );
return result;
}
The critical part here (as I'm sure you've figured out already) is that
prev_pos (the previous position) of the last recursion is combined with
crnt_pos (the current positon) of the present recursion and passed along
to become the prev_pos of the next recursion.
But written this way, I had to remember that any call to func_recurs()
always had to look like this:
func_recurs(arg1, arg2, 0);
Frankly, I thought that constant 0 dangling at the end was rather
inelegant. Then it struck me that maybe I could "hide" func_recurs
inside another function so that I wouldn't have to strain my brain
remembering about that pesky third argument; something like:
func_lazymemory(int arg1, int arg2)
{
func_recurs(arg1, arg2, 0);
}
Being new to C, I felt pretty clever for coming up with this all on my
own. But then I thought: "Bah! Smells of kludge. There must be a
better way."
So I changed it to:
int func_recurs(int arg1, int arg2)
{
--> static int prev_pos; /* conveniently init'd to 0 on 1st call */
|
Just a nit. Static variables are initialized prior to your program
beginning execution and independent of your function.
Remove del for email |
|
| Back to top |
|
 |
Morris Dovey *nix forums addict
Joined: 22 Jun 2005
Posts: 90
|
Posted: Wed Jul 19, 2006 2:01 pm Post subject:
Re: Function Wrapper: Opinions and Critique Desired
|
|
|
I.M. !Knuth (in Xns98055B40DA1711011011@81.174.50.80) said:
| 3) Is there some other (maybe obvious) solution to ditching that
| third argument that I've somehow overlooked?
There is usually some other method (no matter what you're doing) :-)
I have two short pieces of recursive code that you might find
interesting:
http://www.iedu.com/mrd/c/getsm.c and
http://www.iedu.com/mrd/c/getsmx.c that deal with a similar situation.
The two are functionally equivalent; but the second module "cheats" in
that it uses a gcc extension to allow embedding one function
declaration inside another. It's non-standard but may have some value
as a thought-provoking device.
--
Morris Dovey
DeSoto Solar
DeSoto, Iowa USA
http://www.iedu.com/DeSoto |
|
| Back to top |
|
 |
I.M. !Knuth *nix forums beginner
Joined: 26 Jun 2006
Posts: 14
|
Posted: Wed Jul 19, 2006 6:33 am Post subject:
Function Wrapper: Opinions and Critique Desired
|
|
|
A while back, I was mucking around with a recursive function. For
brevity's sake, I'll define it like this:
int func_recurs(int arg1, int arg2, int prev_pos)
{
int crnt_pos = 0;
int result;
/* stuff happens to arg1, arg2, and crnt_pos */
func_recurs(arg1, arg2, (prev_pos + crnt_pos) );
return result;
}
The critical part here (as I'm sure you've figured out already) is that
prev_pos (the previous position) of the last recursion is combined with
crnt_pos (the current positon) of the present recursion and passed along
to become the prev_pos of the next recursion.
But written this way, I had to remember that any call to func_recurs()
always had to look like this:
func_recurs(arg1, arg2, 0);
Frankly, I thought that constant 0 dangling at the end was rather
inelegant. Then it struck me that maybe I could "hide" func_recurs
inside another function so that I wouldn't have to strain my brain
remembering about that pesky third argument; something like:
func_lazymemory(int arg1, int arg2)
{
func_recurs(arg1, arg2, 0);
}
Being new to C, I felt pretty clever for coming up with this all on my
own. But then I thought: "Bah! Smells of kludge. There must be a
better way."
So I changed it to:
int func_recurs(int arg1, int arg2)
{
--> static int prev_pos; /* conveniently init'd to 0 on 1st call */
int crnt_pos = 0;
int result;
/* stuff happens to arg1, arg2, and crnt_pos */
--> prev_pos += crnt_pos; /* adjust for next recursion */
--> func_recurs(arg1, arg2);
--> prev_pos -= crnt_pos; /* restore for current recursion */
return result;
}
Drawing your attention to the four "-->" lines, I then thought: "Boy is
that ugly", but I no longer felt I'd somehow cheated inside my code. I
packed away the function and forgot about it ... until tonight.
Tonight I was browsing through some months' old threads on clc and came
across one that discussed function wrappers. "Cool," I thought. A
response referenced the FAQ, so I pulled it up and had a read. So, my
clever idea is old hat. Figures!
I started thinking again about how I dealt with that function and came
up with some questions and concerns:
1a) Is my use of a wrapper appropriate (or am I ignorant of some wrapper
rule or style convention)?
1b) Wouldn't the wrapper be improved (and the program conserve some
storage) if it were re-written to pass pointer values like this?
func_lazymemory(int *arg1, int *arg2)
{
func_recurs(arg1, arg2, 0);
}
2a) Is one of my solutions better/cleaner/preferable over the other?
2b) Or are they equivalent, and picking one is a matter of (my) personal
style?
3) Is there some other (maybe obvious) solution to ditching that third
argument that I've somehow overlooked?
Thanks for your attention.
--
I.M. (definitely) !Knuth |
|
| Back to top |
|
 |
Google
|
|
| Back to top |
|
 |
|
|
The time now is Fri Nov 21, 2008 10:38 pm | All times are GMT
|
|
Mortgage Loans | MySpace Images | Loans | Xbox Mod Chip | Mortgages
|
|
Copyright © 2004-2005 DeniX Solutions SRL
|
|
|
|
Other DeniX Solutions sites:
Unix/Linux blog |
electronics forum |
medicine forum |
science forum |
|
|
Privacy Policy
|
Powered by phpBB © 2001, 2005 phpBB Group
|
|