Topic : C Lessons
Author : Christopher Sawtell
Page : << Previous 14  Next >>
Go to page :


         /* raw datum value from 8 bit ADC */
  char lower_limit;              /* For alarms. */
  char upper_limit;
  float processed_value;         /* The number to go on screen. */
  float offset;
  float scale_factor;
  int vx;                        /* Position of value on screen. */
  int vy;
  }CHANNEL;

enum units_of_measure { kPa, degC, kW, rpm, Volts, Amps, Newtons };

char *units { "kPa", "degC", "kW", "rpm", "Volts", "Amps", "Newtons" };

CHANNEL data [] =
{
  { "radiator temperature",
  { "radiator pressure",
  { "fuel temperature",
  { "fuel pressure",
  { "oil temperature",
  { "oil pressure",
  { "exhaust manifold temperature",
  { "power output",
  { "torque",
  };

#define NUMBER_OF_INPUTS sizeof (data ) / sizeof ( data[0] )


Now the lesson preparation is to find the single little bug in the above
program fragment, to finish the initialisation of the data array of type
CHANNEL and to have a bit of a crack at creating a screen layout
program to display its contents. Hint: Use printf();
( Leave all the values which originate from the real world as zero. )


  Here are some more tips for young players.

  1) Don't get confused between the logical equality operator,

     ==

     and the assignment to a variable operator.

     =

     This is probably the most frequent mistake made by 'C' beginners, and
     has the great disadvantage that, under most circumstances, the compiler
     will quite happily accept your mistake.

  2) Make sure that you are aware of the difference between the logical
     and bit operators.

     &&         This is the logical AND function.
     ||         This is the logical OR function.
                The result is ALWAYS either a 0 or a 1.

     &          This is the bitwise AND function used for masks etc.
                The result is expressed in all the bits of the word.

  3) Similarly to 2 be aware of the difference between the logical
     complementation and the bitwise one's complement operators.

     !          This is the logical NOT operator.
     ~          This is the bitwise ones complement op.

     Some further explanation is required. In deference to machine efficiency a
     LOGICAL variable is said to be true when it is non-zero. So let's set a
     variable to be TRUE.

     00000000000000000000000000000001  A word representing TRUE.
                                       Now let's do a logical NOT  !.
     00000000000000000000000000000000  There is a all zero word, a FALSE.

     00000000000000000000000000000001  That word again. TRUE.
                                       Now for a bitwise complement  ~.
     11111111111111111111111111111110  Now look we've got a word which is
                                       non-zero, still TRUE.

                                       Is this what you intended?

  4) It is very easy to fall into the hole of getting the
     '{' & '}'; '[' & ']'; '(' & ')'; symbol pairs all messed up and the
     computer thinks that the block structure is quite different from that
     which you intend. Make sure that you use an editor which tells you the
     matching symbol. The UNIX editor vi does this provided that you turn
     on the option. Also take great care with your layout so that the block
     structure is absolutely obvious, and whatever style you choose do take
     care to stick by it throughout the whole of the project.
     A personal layout paradigm is like this:

  Example 1.

function_type function_name ( a, b )
type a;
type b;
{
  type variable_one, variable_two;

  if ( logical_expression )
  {
    variable_one = A_DEFINED_CONSTANT;
    if ( !return_value = some_function_or_other ( a,
                                                  variable_one,
                                                  &variable_two
                                                  )
         )
    {
      error ( "function_name" );
      exit ( FAILURE );
      }
    else
    {
      return ( return_value + variable_two );
      }
    }    /* End of "if ( logical_expression )" block */
  }    /* End of function */


  This layout is easy to do using vi with this initialisation script
  in either the environment variable EXINIT or the file ${HOME}/.exrc:-

set showmode autoindent autowrite tabstop=2 shiftwidth=2 showmatch wm=1

  Example 2.

void printUandG()
{
  char *format =
"\n\
           User is: %s\n\
          Group is: %s\n\n\
Effective User is: %s\n\
Effective Group is: %s\n\n";

  ( void ) fprintf ( tty,
                     format,
                     passwd_p->pw_name,
                     group_p->gr_name,
                     epasswd_p->pw_name,
                     egroup_p->gr_name
                     );
  }


  Notice how it is possible to split up format statements with a '\' as
  the last character on the line, and that it is convenient to arrange
  for a nice output format without having to count the
  field widths. Note however that when using this technique that the '\'
  character MUST be the VERY LAST one on the line. Not even a space may
  follow it!

  In summary I *ALWAYS* put the opening brace on a new line, set the tabs
  so that the indentation is just two spaces, (

Page : << Previous 14  Next >>