You are on page 1of 6

Describing the meanings of programs:

Describing the meaning of a program involves understanding what the program


does when it runs. This includes:

Behavior: What actions the program takes and in what order. For example, it
might read input; perform calculations, and output results.

State Changes: How the program modifies its internal state as it runs. This
includes changes to variables, data structures, and other program elements.

Interactions: How the program interacts with external systems or users. This
could involve reading from or writing to files, communicating over a network, or
responding to user input.

Effects: The overall impact of running the program, such as producing output,
modifying data, or causing side effects.

Describing the meaning of a program typically involves considering its dynamic


semantics—how it behaves when executed—rather than just its static structure or
syntax. This understanding helps programmers debug code, predict its behavior,
and ensure it behaves as intended.

Dynamic semantics:

 Dynamic semantics refers to the meaning or behavior of a program as it


executes.
 It deals with how statements and expressions in a programming language
interact with each other and with the computer's environment during
runtime.
 Dynamic semantics describes what happens when the program is run,
including how variables are assigned values, how functions are called, how
control structures like loops and conditionals are executed, and how memory
is managed.
 Dynamic semantics is about understanding what our code actually does
when it's running.
 It involves studying the interactions and effects of various program elements
as they execute, which is crucial for understanding and debugging code.
Operational semantics

 Operational semantics helps us understand what a statement or program does


by specifying what happens when it runs on a machine.
 The changes in the machine are perceived as a series of alterations in its
state, where the machine's state represents the compilation of values in its
storage,
 One straightforward way to describe operational semantics is by running a
compiled version of the program on a computer and observing its behavior.
 The machine languages and real computers are not used for formal
operational semantics.

Rather, intermediate-level languages and interpreters for idealized computers are


designed specifically for the process.

There are different levels of uses of operational semantics.

At the highest level, the interest is in the final result of the execution of a
complete program. This is sometimes called natural operational semantics.

At the lowest level, operational semantics can be used to determine the precise
meaning of a program through an examination of the complete sequence of
state changes that occur when the program is executed.

Example

Consider a simple program written in a hypothetical programming language that


adds two numbers and prints the result.

int main() {

int a = 5;

int b = 7;

int sum = a + b;

print(sum);

return 0;}
The operational semantics by executing this compiled program on a computer:

1. Assign Values: The first step is to allocate memory for variables a, b, and
sum and assign them their initial values: a = 5, b = 7.

2. Perform Addition: Next, the computer performs the addition operation a + b,


which results in sum = 12.

3. Print Result: After calculating the sum, the program prints the value of sum,
which is 12.

4. Return: Finally, the program returns 0 to indicate successful execution.

By executing this compiled program on a computer, we observe the sequence of


changes in the computer's state:

 Memory is allocated and initialized for variables a, b, and sum.

 The values of a and b are added to compute the value of sum.

 The value of sum is printed to the screen.

 The program terminates with a return value of 0.

This sequence of changes in the computer's state provides us with an understanding


of the operational semantics of the program, showing how each step of execution
affects the computer's state.

Denotational semantics

Denotational semantics provides a rigorous and widely accepted formal method for
describing the meaning of programs. It is grounded in recursive function theory,
which enables precise definitions of programming language constructs and
their meanings.

We have a simple programming language that supports basic arithmetic operations


like addition and multiplication. We want to define the denotational semantics
for this language, which involves assigning mathematical objects to language
constructs.
For example, consider the addition operation.

In denotational semantics, we define a mathematical function that represents


the meaning of addition. This function takes two numbers as input and produces
their sum as output. So, for the addition operation in our programming language,
we define a function like this:

Add : Number + Number -> Number

Add(x,y) = x + y

Here, the function add takes two numbers x and y as inputs (the syntactic domain)
and returns their sum as the output (the semantic domain).

Similarly, we can define functions for other language constructs like


multiplication, subtraction, and division.

By defining these mathematical functions for each language construct, we establish


a mapping between the syntactic structures of the programming language and their
corresponding mathematical objects. This mapping captures the precise meaning of
each language entity.

The main idea behind denotational semantics is that mathematical objects provide
a rigorous way to model the meaning of programming language constructs. Unlike
operational semantics, denotational semantics does not focus on the step-by-step
execution of programs but rather on establishing mathematical relationships
between language constructs and their meanings.

In denotational semantics, mapping functions play a important role. Just like any
mathematical function, they have a domain and a range.

 Domain: The domain consists of all the valid inputs (or parameters) for the
function. In denotational semantics, this domain is referred to as the
syntactic domain because it represents the syntactic structures of the
programming language being mapped.

 Range: The range comprises the resulting objects to which the parameters
are mapped. This range is known as the semantic domain in denotational
semantics because it represents the meaning or semantics assigned to the
syntactic structures.

Example:

Consider a simple programming language that has a construct for adding two
numbers together, written as add(x, y). In denotational semantics, we can define a
mapping function for this construct.

 Domain (Syntactic Domain): The parameters x and y are the valid inputs to
our mapping function. They represent the syntactic structures of our
programming language.

 Range (Semantic Domain): The result of adding x and y is the object to


which these parameters are mapped. This represents the semantic meaning
of the addition operation.

So, in this example:

 Domain: The syntactic domain consists of pairs of numbers, (x, y), where x
and y are valid numerical values in our programming language.

 Range: The semantic domain consists of the sum of x and y, which is a


numerical value representing the result of the addition operation.

Axiomatic semantics

 Axiomatic semantics is a method for understanding programs based on


mathematical logic.
 It is the abstract way to specify what a program does.
 Instead of directly saying what a program means, axiomatic semantics
focuses on what can be proven about it.
 One important use of this method is to check if programs are correct.
 Unlike other approaches, axiomatic semantics doesn't keep track of every
detail of how a program runs or changes the computer's state.
 Instead, it looks at the relationships between different parts of the program,
like variables and constants.
 These relationships stay the same every time the program runs.
 Axiomatic semantics has two main purposes: verifying programs and
describing how they work.
 Verifying means proving that a program does what it's supposed to do.
 Axiomatic semantics helps with this by using logical expressions for each
part of the program.
 These expressions set rules for variables, showing what must be true before
and after each part of the program runs.
 We don't need to look at the whole program state, just these rules.
 We use a type of math called predicate calculus to write these rules.
 While simple rules like "x > 0" can be enough, sometimes we need more
complex logic.

For example, if we have a statement like "x = x + 1" in our program, in axiomatic
semantics, we'd set a rule like "{ x > 0 } x = x + 1 { x > 1 }".

This means if x starts as a number greater than 0, after running the statement, it
will be greater than 1.

These rules help us understand how each part of the program affects the data it
works with.

You might also like