**Due: Thursday, Sept 29th by 11:59 PM**

## Getting Started

Download fa.scm. Open it in DrRacket.

## Your Task

Your task is to implement the simulation of a deterministic finite automaton, or DFA. The simulation, given a DFA and an input string, will use the DFA to process the string and determine whether the DFA accepts or rejects the string. If the string is accepted, the simulation produces a path (sequence of states) through the DFA, from the start state to a final (accepting) state.

You will need to define three procedures: **dfa-is-final-state?**,
**dfa-find-transition**, and **dfa-simulate**.

### Background

This program uses the **define-datatype** construct defined by the **eopl**
variant of Scheme. Read Section 2.4 in the textbook for an overview
of how **define-datatype** works.

Three datatypes are defined: **dfa-transition**, **dfa-path**, and **dfa**.

The **dfa-transition** datatype represents a single transition in a DFA.
A valid DFA transition will specify a from state, a to state, and a
symbol. It represents the existence of a transition connecting the
from state to the to state, consuming the designated symbol.

The **dfa-path** datatype represents a sequence of states connected by
transitions, starting with the start state.
It is represented by a list containing the sequence of states *in reverse order*.

The **dfa** datatype represents a DFA. It consists of a designated start
state, a designated list of final (accepting) states, and a list
of transitions (which are instances of the **dfa-transition** datatype).

There are detailed comments in **fa.scm** describing the contents of these
data types.

Note that the **dfa-transition** and **dfa-path** data types both have an
*invalid* variant.

- In the case of
**dfa-transition**, the invalid variant is used by the**dfa-find-transition**procedure to indicate that a transition does not exist. - In the case of
**dfa-path**, the invalid variant is used by the**dfa-simulate**procedure to indicate that an input string is rejected by the DFA

### dfa-is-final-state?

This procedure takes as parameters a dfa and a state, and returns **#t**
if the state is a final state and **#f** if the state is not a final state.

### dfa-transition-find

This procedure takes as parameters a dfa, a from state, and a symbol, and returns

- a valid transition whose from state and symbol match the ones given as parameters, or
- an invalid transition if no such transition exists in the DFA

### dfa-simulate

This procedure takes as parameters a dfa and an input string (represented as a list of symbols). It returns

- a valid path if the string is accepted by the dfa, where the list of states in the path corresponds to the states traversed while processing the string, or
- an invalid path if the string is rejected by the dfa

## Hints

Start by implementing the **dfa-is-final-state?** procedure.

Next, implement the **dfa-find-transition** procedure.

Finally, implement **dfa-simulate**. The **dfa-is-final-state?** and
**dfa-find-transition** procedures should be useful.

You can use the **eq?** procedure to test two symbol values to see if
they are the same symbol:

You can use the **=** procedure to test whether or not two state values
are the same state, since integer values are used to represent states.

Use the **dfa-path-extend** procedure to append a new state onto
an existing path, creating a new (extended) path. This procedure will
be useful in your implementation of **dfa-simulate**.

A global variable called **odd-as** is an instance of the **dfa** datatype
which recognizes all strings of a's and b's containing an odd number of a's:

A global variable called **no-abb** is an instance of the **dfa** datatype
which recognizes all strings of a's and b's which do not contain the
substring **abb**:

As you implement each procedure, you can test it using **odd-as** and **no-abb**
as test DFA instances. Here is a transcript showing the expected results
of the procedures (user input in **bold**):

>(dfa-is-final-state? odd-as 1)#f >(dfa-is-final-state? odd-as 2)#t >(dfa-is-final-state? no-abb 1)#t >(dfa-is-final-state? no-abb 2)#t >(dfa-is-final-state? no-abb 3)#t >(dfa-find-transition odd-as 1 'a)#(struct:valid-dfa-transition 1 2 a) >(dfa-find-transition odd-as 1 'b)#(struct:valid-dfa-transition 1 1 b) >(dfa-find-transition no-abb 3 'a)#(struct:valid-dfa-transition 3 2 a) >(dfa-find-transition no-abb 3 'b)#(struct:invalid-dfa-transition) >(dfa-simulate no-abb '(b b b b))#(struct:valid-dfa-path (1 1 1 1 1)) >(dfa-simulate no-abb '(a b a b))#(struct:valid-dfa-path (3 2 3 2 1)) >(dfa-simulate no-abb '(a a a b))#(struct:valid-dfa-path (3 2 2 2 1)) >(dfa-simulate no-abb '(a a a b b))#(struct:invalid-dfa-path)

## Submitting

Submit your modified version of **fa.scm** to Marmoset as **assign3**:

https://cs.ycp.edu:8443/

**IMPORTANT**: after uploading, you should download a copy of your submission and
double-check it to make sure that it contains the correct file(s). You are
responsible for making sure your submission is correct. You may receive a grade
of 0 for an incorrectly submitted assignment.