Problem Solving Using C++

Modular Programming Concepts and C++ Architecture

  • Modular Program Definition:

    • A program consisting of interrelated segments, known as modules, arranged in a logical and understandable structure.

    • Designed to make softare easier to develop, correct, and modify over time.

  • Primary C++ Modular Building Blocks:

    • Functions: Accept input, process the input internally, and produce output. Processing logic inside a function is encapsulated and hidden from external view.

    • Classes: Encapsulate both data structures and the operations/functions that manipulate that data.

Conceptual model of function encapsulation

C++ Identifiers, Rules, and Keywords

  • Identifier Definition:

    • A custom name given by the programmer to elements of the language, such as classes, functions, or variables.

  • Naming Rules for Identifiers:

    • The initial character must be an alphabetic letter (A−ZA-Z, a−za-z) or an underscore (_).

    • Subsequent characters may only consist of letters, digits (0−90-9), or underscores.

    • White spaces and special characters (e.g., *, -, !) are forbidden.

    • Reserved keywords cannot be used as identifiers.

    • Maximum legal length of an identifier is 10241024 characters.

    • C++ is strictly case-sensitive (density and Density represent distinct identifiers).

  • Examples of Identifiers:

    • Valid Identifiers: degToRad, intersect, addNums, slope, bessell, multTwo, findMax, density.

    • Invalid Identifiers:

    • 1AB3 (begins with a numerical digit).

    • E*6 (contains the invalid special character *).

    • while (violates the rule against using language keywords).

  • Keywords:

    • Reserved names that represent built-in functions, objects, or language constructs.

Reserved Keywords Table
  • Full List of Reserved C++ Keywords:

    • auto, break, case, catch, char, class, const, continue, default, delete, do, double, else, enum, extern, float, for, friend, goto, if, inline, int, long, new, overload, private, protected, public, register, return, short, signed, sizeof, static, struct, switch, template, this, typedef, union, unsigned, virtual, void, volatile, while.

  • Function Identifiers:

    • Defined with a mandatory pair of parentheses appended to the identifier name (e.g., easy(), c3po(), r2d2(), theForce()).

    • Should follow descriptive mnemonic naming standards.

The main() Driver Function Structure

  • Main Function Architecture:

    • Every executable C++ program requires exactly one main() function, which operates as the driver function.

    • Program execution begins in main(), which directs and calls all other modules or helper functions.

Driver function interaction with modules
  • Anatomic Components of a Function:

    • Function Header Line: The introductory line defining the return data type, function name, and parameter list.

    • Arguments / Parameters: Data values passed into the function upon invocation.

    • Function Body: Program execution statements enclosed within opening ({) and closing (}) braces.

Structure of the main function header and body
  • Statement Execution and Termination Rules:

    • Every statement inside a function body must terminate with a semicolon ;.

    • return: Reserved keyword that exits the function and returns a value to the calling environment.

    • return 0; placed at the conclusion of main() signals successful program termination to the operating system.

Standard Output and Preprocessor Commands

  • Output Stream (cout):

    • An predefined output stream object that delivers data to the standard output device (typically the console/screen).

    • Combined with the insertion operator << to send strings or values to output.

  • Preprocessor Directives:

    • Lines beginning with # evaluated before source code compilation into object machine code.

    • #include <filename>: Directs the preprocessor to copy the content of the specified header file into the source file.

    • Header Files: Libraries positioned at the top of code files; <iostream> provides standard input/output stream capabilities.

  • Namespaces:

    • Syntax: using namespace std;

    • Specifies the default scope where standard system identifiers are defined, preventing naming collisions between user functions and standard library modules.

  • String Literals and Delimiters:

    • String Literal: Text characters (letters, numbers, special symbols) enclosed in double quotes.

    • Delimiter: Double quote symbols (") marking the boundary of a string literal; delimiters are not printed or stored as part of string data.

  • Console Output Demonstration Programs:

Program 2.1 Code
#include <iostream>
using namespace std;

int main()
{
    cout << "Hello there world!";
    return 0;
}
Program 2.2 Code
#include <iostream>
using namespace std;

int main()
{
    cout << "Computers, computers everywhere";
    cout << "
 as far as I can C";
    return 0;
}
Program 2.3 Code
#include <iostream>
using namespace std;

int main()
{
    cout << "Computers everywhere
 as far as

I can see";
    return 0;
}
  • Escape Sequences:

    • Combinations of characters starting with a backslash \ that instruct the compiler to perform special display formatting.

    • : Escape sequence for inserting a newline character.

Formatting, Style, and Program Comments

  • Code Formatting Standards:

    • Limit statements to one per line.

    • Place function braces {} on dedicated lines aligned with the function block.

    • Indent all code statements contained within a function body.

  • Code Documentation Methods:

    • Single-line comments: Commenced with // and extend to the end of that specific line.

    • Multi-line / Block comments: Enclosed between starting /* and ending */ markers.

Primitive C++ Data Types and ASCII Standards

  • Data Type Definition:

    • A defined set of values coupled with legal operations allowed on those values.

    • Category Split: Built-in primitive types (standard compiler types) versus User-defined class types.

Built-in Data Types Hierarchy
  • Built-In Data Type Operations:

Operations on Primitive Types
  • Integer Types: Supported operators include +, -, *, /, %, =, ==, !=, <=, >=, sizeof(), and bitwise operators.

  • Floating Point Types: Supported operators include +, -, *, /, =, ==, !=, <=, >=, sizeof().

    • Integer Data Groupings:

Integer Data Types Tree
  • The Nine Primitive Integer Subtypes:

    • bool, char, short int, int, long int, unsigned char, unsigned short int, unsigned int, unsigned long int.

    • int: Stores positive and negative whole numbers without decimal places.

    • char: Stores a single character enclosed in single quotation marks (e.g., 'A').

  • Character Encoding (ASCII Standards):

ASCII Codes Table
  • Binary Codes for Uppercase ASCII Characters:

    • A: 01000001, B: 01000010, C: 01000011, D: 01000100, E: 01000101, F: 01000110

    • G: 01000111, H: 01001000, I: 01001001, J: 01001010, K: 01001011, L: 01001100

    • M: 01001101, N: 01001111, O: 01001110, P: 01010000, Q: 01010001, R: 01010010

    • S: 01010011, T: 01010100, U: 01010101, V: 01010110, W: 01010111, X: 01011000

    • Y: 01011001, Z: 01011010

    • Character Storage Example:

  • Storing string BARTER requires 66 individual bytes of memory, where each byte contains the corresponding ASCII binary bit pattern.

Memory byte representation of BARTER
  • Boolean Data Type (bool):

    • Stores logical binary condition state: true or false.

  • Memory Allocation Determination via sizeof() Operator:

    • The sizeof() operator returns the exact system byte size allocated for a data type or variable.

Program 2.5 Code
#include <iostream>
using namespace std;

int main()
{
    cout << "
Data Type  Bytes"
         << "
---------  -----"
         << "
int        " << sizeof(int)
         << "
char       " << sizeof(char)
         << "
bool       " << sizeof(bool)
         << '
';
    return 0;
}
  • Integer Data Type Allocation and Range Limits:

Integer Data Type Storage Table
  • char: Storage = 11 byte; Value Range = 256256 characters.

  • bool: Storage = 11 byte; Value Range = true (any positive value) and false (00).

  • short int: Storage = 22 bytes; Value Range = −32,768-32,768 to +32,767+32,767.

  • unsigned short int: Storage = 22 bytes; Value Range = 00 to 65,53565,535.

  • int: Storage = 44 bytes; Value Range = −2,147,483,648-2,147,483,648 to +2,147,483,647+2,147,483,647.

  • unsigned int: Storage = 44 bytes; Value Range = 00 to 4,294,967,2954,294,967,295.

  • long int: Storage = 44 bytes; Value Range = −2,147,483,648-2,147,483,648 to +2,147,483,647+2,147,483,647.

  • unsigned long int: Storage = 44 bytes; Value Range = 00 to 4,294,967,2954,294,967,295.

    • Floating-Point Data Types:

  • Represents real numbers containing explicit decimal fractions.

Floating Point Types Specifications
  • float: Storage = 44 bytes; Absolute Value Range = 1.40129846432481707×10−451.40129846432481707 \times 10^{-45} to 3.40282346638528860×10383.40282346638528860 \times 10^{38}.

  • double and long double: Storage = 88 bytes; Absolute Value Range = 4.94065645841246544×10−3244.94065645841246544 \times 10^{-324} to 1.79769313486231570×103081.79769313486231570 \times 10^{308}.

  • Floating Point Literal Literals Suffixes:

    • 9.234: Unsuffixed floating-point literal defaults to type double.

    • 9.234F or 9.234f: Forces type float.

    • 9.234L or 9.234l: Forces type long double.

Arithmetic Expressions and Operator Precedence

  • Binary vs Unary Operators:

    • Binary Operators: Require two operands to execute an operation.

    • Unary Operators: Require a single operand (e.g., unary minus - used to reverse numeric sign).

Basic Arithmetic Operators Table
  • Addition Operator: +

  • Subtraction Operator: -

  • Multiplication Operator: *

  • Division Operator: /

  • Modulus Division Operator: %

    • Demonstration of Arithmetic Operations (Program 2.6):

Program 2.6 Code
#include <iostream>
using namespace std;

int main()
{
    cout << "15.0 plus 2.0 equals " << (15.0 + 2.0) << endl
         << "15.0 minus 2.0 equals " << (15.0 - 2.0) << endl
         << "15.0 times 2.0 equals " << (15.0 * 2.0) << endl
         << "15.0 divided by 2.0 equals " << (15.0 / 2.0) << endl;
    return 0;
}
  • Expression Types and Division Principles:

    • Integer Expressions: Expressions evaluated strictly with integer operands.

    • Integer Division Rules: When dividing two integer values, fractional decimal results are truncated (e.g., 15/215 / 2 yields 77).

    • Modulus Operator (%): Computes and returns only the integer remainder of division (e.g., 9%49 \% 4 yields 11).

    • Mixed-Mode Expressions: Expressions combining integer and floating-point data types. The result evaluates to a double-precision floating-point value.

  • Rules for Constructing Arithmetic Expressions:

    • Never place two binary arithmetic operators directly adjacent to each other.

    • Use parentheses () to enforce evaluation order; nested expressions evaluate from the innermost set outward.

    • Explicitly use the * symbol for multiplication; adjacent parentheses do not implicitly multiply.

  • Precedence and Associativity Rules:

Operator Precedence and Associativity Table
  • Priority Hierarchy:

    1. Unary - (Negation): Evaluated with Right-to-Left associativity.

    2. *, /, %: Higher precedence, evaluated with Left-to-Right associativity.

    3. +, -: Lower precedence, evaluated with Left-to-Right associativity.

Variables, Memory Address Allocation, and Declarations

  • Variables and Memory Storage:

    • Variable: A named symbolic identifier assigned to a specific computer memory address holding data.

Memory storage locations for integersMapping variable names to addresses
  • Assignment Statements:

    • Stores a calculated value into the assigned memory space of a variable.

    • Syntax: variableName = expression;

    • Examples: num1 = 45;, num2 = 12;, total = num1 + num2;.

  • Declaration Statements:

    • Informs the compiler of the data type and identifier name, allocating required physical memory.

    • Syntax: dataType variableName; (e.g., int sum;).

    • Multiple variables of identical types can be declared together: double grade1, grade2, total, average;.

    • Variables can be assigned initial values during declaration: double grade1 = 85.5;.

    • Mandatory Rule: A variable must be declared prior to its use in any statement.

Program 2.7a Code
#include <iostream>
using namespace std;

int main()
{
    double grade1 = 85.5;
    double grade2 = 97.0;
    double total, average;

    total = grade1 + grade2;
    average = total / 2.0; // divide the total by 2.0
    cout << "The average grade is " << average << endl;

    return 0;
}
  • Variable Attributes and Memory Address Retrieval:

    • Three essential traits associated with a variable:

    1. Data Type.

    2. Stored Value (Memory contents).

    3. Physical Memory Address.

    • Address Operator (&): Symbol placed before a variable name to retrieve its physical memory address.

Memory tagging visual for float slopeProgram 2.10 Code
#include <iostream>
using namespace std;

int main()
{
    int num;

    num = 22;
    cout << "The value stored in num is " << num << endl;
    cout << "The address of num = " << &num << endl;

    return 0;
}

Engineering Software Development and Radar Speed Trap Case Study

  • Four-Step Software Problem-Solving Protocol:

    • Step 1: Analyze the Problem (Identify necessary input parameters and expected output results).

    • Step 2: Develop a Solution (Formulate algorithms using top-down structured design).

    • Step 3: Code the Solution (Translate algorithm logic into C++ source code).

    • Step 4: Test and Correct Program (Validate computed outputs against manual calculations and edge cases).

  • Radar Speed Trap Case Study:

    • System Analysis:

    • Desired Output: Vehicle speed in miles per hour.

    • System Inputs: Transmitted radar frequency (fef_e) and received reflected frequency (frf_r).

    • Mathematical Formulation:

    • Formula: speed=6.685×108×fr−fefr+fe\text{speed} = 6.685 \times 10^8 \times \frac{f_r - f_e}{f_r + f_e}

Program 2.11 Code
#include <iostream>
using namespace std;

int main()
{
    double speed, fe, fr;

    fe = 2e10;
    fr = 2.0000004e10;

    speed = 6.685e8 * (fr - fe) / (fr + fe);
    cout << "The speed is " << speed << " miles/hour " << endl;

    return 0;
}

Common Programming Mistakes

  • Syntactical and Structural Errors:

    • Omitting parentheses after main.

    • Omitting or misplacing curly braces { or }.

    • Misspelling language keywords or library function identifiers.

    • Forgetting quotation marks around literal output strings passed to cout.

    • Omitting the terminating semicolon at the end of a statement.

    • Improperly appending a semicolon to preprocessor directives like #include <iostream>.

    • Forgetting newline escape sequences ( or endl), causing continuous text wrapping.

    • Visual substitutions between character 'O' and numeric digit '0', or lowercase 'l' and digit '1'.

  • Algorithmic and Memory Errors:

    • Using variables without prior declaration.

    • Assigning incompatible data types into declared variables.

    • Attempting calculations using uninitialized variables containing garbage values.

    • Unexpected integer division results caused by omitting floating-point constants.

    • Unintended precision loss from mixing binary arithmetic types.