pushing what I hace currently.

This commit is contained in:
Alex Huddleston 2017-10-24 08:49:03 -05:00
parent 52fcda3b1a
commit 46d724dd9d
16 changed files with 11383 additions and 0 deletions

BIN
hw1/.hw1pr1.cpp.swp Normal file

Binary file not shown.

5000
hw1/.hw1pr2_data.txt Normal file

File diff suppressed because it is too large Load diff

133
hw1/420hw1-17fall.txt Normal file
View file

@ -0,0 +1,133 @@
(Print this page as a cover sheet for your printouts)
CSCE 420 HOMEWORK 1 (UPDATED)
Dr. Daugherity
Section: ______________
Due: 11:59 P.M. Monday, October 2, 2017
"On my honor, as an Aggie, I have neither given nor received any unauthorized
aid on any portion of the academic work included in this assignment."
________________________________ ________________________________
Typed or printed name of student Signature of student
NOTE: Please follow your lab instructor's directions for submitting your
assignment through CSNET. ONLY ASSIGNMENTS SUBMITTED TO CSNET WILL BE GRADED!
Make a printout of each source file and staple it behind this cover sheet.
Sign it and turn it in in class Tuesday. IF YOU DO NOT TURN IN A SIGNED COVER
SHEET YOUR WORK WILL NOT BE GRADED!
NOTE: Homework will be graded on build.tamu.edu, using g++ 7.2.0 with
-std=c++17, or javac and java, or python3.6 (not python or python2 or python3).
You are free to develop your programs on any other platform, but it is your
responsibility to make sure your programs also compile and execute correctly on
build.tamu.edu as specified.
NOTE: Each file submitted (hw1pr1.cpp, etc.--see below) must begin as follows:
//Your name and UIN
//CSCE 420
//Due: Ocotber 2, 2017
//hw1pr1.cpp (or whatever this file name is)
NOTE: Also write a README.txt file with whatever information is needed to
compile and run your programs. Zip the README.txt and the homework files into
a single file named hw1.zip and submit to CSNET.
The grade for this lab will be based on style (formatting, variable names,
comments, etc.), syntax (no compilation or link errors), and correctness
(passes all test cases). Your grade for this lab is:
Problem # 1 2 3 4
Style /2 /4 /4 /2
Syntax /3 /6 /6 /3
Correctness /5 /10 /10 /5
-------------------------------------------------------------------
Total /10 /20 /20 /10
Grand total _____/50
1. (10 points) Given a file containing a list of points (x,y) in the plane,
write a greedy best-first search to find a closed path connecting all the
points (the "Travelling Salesperson Problem") and output its length. You may
assume that x and y are non-negative integers that will fit in a 32-bit int.
Each line of input will be the x and y coordinates for a point; keep reading
until EOF. You may assume there will be no more than 10000 points and that
the input file will be named hw1pr1_data.txt.
For example, if the input file contains
0 0
0 1
1 1
1 2
the output to the screen is (probably)
0 0
0 1
1 1
1 2
5.236
The run time should be 60 seconds or less for up to 10000 points. Hint: use
the UNIX timeout command to automatically stop execution after 60 seconds.
Name your program hw1pr1.cpp or Hw1Pr1.java or hw1pr1.py.
2. (20 points) The shortest closed path for the example points in problem 1 is
actually 4.828. In other words, greeedy best-first search did not find the
shortest path. Modify your program for problem 1 to do an iterative deepening
search to the depth of the number of points, with the path cost the total
distance. To keep the search space manageable only include the 4 nearest
unvisited points as successors when you expand a node.
The run time should be 60 seconds or less for up to 10000 points. Hint: use
the UNIX timeout command to automatically stop execution after 60 seconds.
Name your program hw1pr2.cpp or Hw1Pr2.java or hw1pr2.py.
3. (20 points) Write a breadth-first search program to solve 15-puzzle problems
in the same way as the 8-puzzle in Figure 3.4 on page 71. Keep track of the
number of nodes expanded and print that out along with the steps to solve the
problem. Define the legal moves as "swap the blank with an adjacent tile,"
resulting in the blank's moving up, down, left, or right. A sample run should
look like this:
Enter 15-puzzle starting state by rows (0 for blank):
1,2,3,4,5,6,7,8,9,10,0,11,13,14,15,12
Enter ending state by rows (0 for blank):
1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,0
Solution:
Start 1 2 3 4
5 6 7 8
9 10 0 11
13 14 15 12
Swap the blank
Right 1 2 3 4
5 6 7 8
9 10 11 0
13 14 15 12
Down 1 2 3 4
5 6 7 8
9 10 11 12
13 14 15 0
Done! Generated xx states.
Note: To keep the time and memory requirements reasonable, your program only
needs to solve 15-puzzle problems which have a solution in 10 moves or less.
Name your program Hw1Pr3.java or hw1pr3.cpp or hw1pr3.py.
OPTIONAL EXTRA CREDIT
=====================
4. (10 points) Modify problem 3 to use A* or IDA* search with Manhattan
distance for h; e.g., the starting state on page 103 has a Manhattan distance
of 18 from the goal state (the sum of the number of rows and columns each tile
must move from its starting position to its ending position). You should see
a marked reduction in the number of states generated, especially for problems
which require more moves. Here is a puzzle which requires 80 moves:
Enter 15-puzzle starting state by rows (0 for blank):
0,12,11,13,15,14,10,9,3,7,6,2,4,8,5,1
Enter ending state by rows (0 for blank):
1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,0
Your program should solve it in 60 seconds or less. Name your program
Hw1Pr4.java or hw1pr4.cpp or hw1pr4.py.

15
hw1/README.txt Normal file
View file

@ -0,0 +1,15 @@
reference for async pthreads: http://www.cplusplus.com/reference/future/future/wait_for/
All other references used pretty much came from cplusplus.com
To compile and run:
I made a makefile that should compile the program regardless of the OS, but only tested linux.
commands should be:
compile: make, make clean
run: ./hw1prX
where X is the problem number.

BIN
hw1/hw1.zip Normal file

Binary file not shown.

225
hw1/hw1pr1/hw1pr1.cpp Normal file
View file

@ -0,0 +1,225 @@
// Alexander Huddleston
// 10/2/17
// hw1pr1.cpp
// Read a file of points, compute greedy best-first of a closed path between points.
#include<stdio.h>
#include<iostream>
#include<fstream>
#include<cmath>
#include<future>
#include<chrono>
#include<vector>
#include<climits>
#include<unordered_set>
using namespace std;
// Double vector used to store list of squared distances between points.
vector<vector<long int>> dmat;
vector<tuple<int, int>> points;
unordered_set<long int> relaxed_edges;
void store_points(ifstream *input, string filename)
{
input->open(filename);
string line = "";
string token = "";
tuple<int, int> temp_point;
get<0>(temp_point) = 0.0;
get<1>(temp_point) = 0.0;
while(getline(*input, line))
{
for(char c : line)
{
if(c == ' ')
{
get<0>(temp_point) = stof(token);
token = "";
}
else
{
token = token + c;
}
}
get<1>(temp_point) = stof(token);
token = "";
points.push_back(temp_point);
}
input->close();
}
void store_distances()
{
long int d1 = 0.0;
long int d2 = 0.0;
tuple< int, int> x;
tuple< int, int> y;
get<0>(x) = 0.0;
get<1>(x) = 0.0;
get<0>(y) = 0.0;
get<1>(y) = 0.0;
vector<long int> tempvec;
for(int r = points.size() - 1; r >= 0; --r)
{
for(int c = 0; c < points.size() - (points.size() - r); ++c)
{
x = points.at(r);
y = points.at(c);
d1 = (get<0>(x) - get<0>(y));
d2 = (get<1>(x) - get<1>(y));
tempvec.push_back(d1*d1 + d2*d2);
}
dmat.push_back(tempvec);
tempvec.clear();
}
}
bool is_visited(vector<int> relaxed_edges, int index)
{
for(int x : relaxed_edges)
{
if(x == index)
{
return true;
}
}
return false;
}
long double best_first(ifstream *input, string filename)
{
// First, store the points from the file into global vector.
store_points(input, filename);
// Small optomization so we don't have to call points.size() so much.
long int n = points.size();
// Store squared distances into dmat.
// Ignore duplicate distances, 0 vectors.
store_distances();
// Find best-first shortest path.
// Keep edges we've already visited.
// Store distance up to this point.
long double current_distance = 0;
// Using this to keep track of selected node.
long int current_node = 0;
long int selected_node = 0;
// Using this to keep track of min distance.
long int min_distance = 0;
while(relaxed_edges.size() < (n - 1))
{
min_distance = INT_MAX;
for(int i = 0; i < (n - 1); ++i)
{
while(relaxed_edges.find(i) != relaxed_edges.end())
{
++i;
if(i == current_node)
{
++i;
}
}
if(i > (n - 1))
{
break;
}
if(i < current_node)
{
if(min_distance > dmat.at(i).at((n - 1) - current_node))
{
selected_node = ((n - 1) - i);
min_distance = dmat.at(i).at((n - 1) - current_node);
}
}
else
{
if(i == current_node)
{
++i;
if(i > (n - 1))
{
break;
}
}
if(min_distance > dmat.at(current_node).at((n - 1) - i))
{
selected_node = ((n - 1) - i);
min_distance = dmat.at(current_node).at((n - 1) - i);
}
}
}
relaxed_edges.insert((n - 1) - current_node);
current_node = selected_node;
current_distance += sqrt(min_distance);
}
current_distance += sqrt(dmat.at(current_node).at(0));
return current_distance;
}
int main()
{
ifstream input;
string filename = "hw1pr1_data.txt";
future<long double> fut = async(best_first, &input, filename);
chrono::milliseconds span(60000);
while((fut.wait_for(span)==future_status::timeout) || input.is_open())
{
}
if(input.is_open())
{
input.close();
}
long double total = fut.get();
tuple<int, int> tempx;
tuple<int, int> tempy;
long int temp;
for(long int i : relaxed_edges)
{
tempx = points.at(temp);
tempy = points.at(i);
cout << get<0>(tempx) << "\t" << get<1>(tempx) << "\t" << get<0>(tempy) << "\t" << get<1>(tempy) << endl;
temp = i;
}
cout << total << endl;
return 0;
}

5000
hw1/hw1pr1/hw1pr1_data.txt Normal file

File diff suppressed because it is too large Load diff

5
hw1/hw1pr1/makefile Normal file
View file

@ -0,0 +1,5 @@
all: main.o
main.o: hw1pr1.cpp
g++ -std=c++17 -lpthread hw1pr1.cpp -o hw1pr1
clean:
rm -rf *.o hw1pr1

225
hw1/hw1pr2.cpp Normal file
View file

@ -0,0 +1,225 @@
// Alexander Huddleston
// 10/2/17
// hw1pr2.cpp
// Read a file of points, compute interative best-first of a closed path between points.
#include<stdio.h>
#include<iostream>
#include<fstream>
#include<cmath>
#include<future>
#include<chrono>
#include<vector>
#include<climits>
#include<unordered_set>
using namespace std;
// Double vector used to store list of squared distances between points.
vector<vector<long int>> dmat;
vector<tuple<int, int>> points;
unordered_set<long int> relaxed_edges;
void store_points(ifstream *input, string filename)
{
input->open(filename);
string line = "";
string token = "";
tuple<int, int> temp_point;
get<0>(temp_point) = 0.0;
get<1>(temp_point) = 0.0;
while(getline(*input, line))
{
for(char c : line)
{
if(c == ' ')
{
get<0>(temp_point) = stof(token);
token = "";
}
else
{
token = token + c;
}
}
get<1>(temp_point) = stof(token);
token = "";
points.push_back(temp_point);
}
input->close();
}
void store_distances()
{
long int d1 = 0.0;
long int d2 = 0.0;
tuple< int, int> x;
tuple< int, int> y;
get<0>(x) = 0.0;
get<1>(x) = 0.0;
get<0>(y) = 0.0;
get<1>(y) = 0.0;
vector<long int> tempvec;
for(int r = points.size() - 1; r >= 0; --r)
{
for(int c = 0; c < points.size() - (points.size() - r); ++c)
{
x = points.at(r);
y = points.at(c);
d1 = (get<0>(x) - get<0>(y));
d2 = (get<1>(x) - get<1>(y));
tempvec.push_back(d1*d1 + d2*d2);
}
dmat.push_back(tempvec);
tempvec.clear();
}
}
bool is_visited(vector<int> relaxed_edges, int index)
{
for(int x : relaxed_edges)
{
if(x == index)
{
return true;
}
}
return false;
}
long double best_first(ifstream *input, string filename)
{
// First, store the points from the file into global vector.
store_points(input, filename);
// Small optomization so we don't have to call points.size() so much.
long int n = points.size();
// Store squared distances into dmat.
// Ignore duplicate distances, 0 vectors.
store_distances();
// Find best-first shortest path.
// Keep edges we've already visited.
// Store distance up to this point.
long double current_distance = 0;
// Using this to keep track of selected node.
long int current_node = 0;
long int selected_node = 0;
// Using this to keep track of min distance.
long int min_distance = 0;
while(relaxed_edges.size() < (n - 1))
{
min_distance = INT_MAX;
for(int i = 0; i < (n - 1); ++i)
{
while(relaxed_edges.find(i) != relaxed_edges.end())
{
++i;
if(i == current_node)
{
++i;
}
}
if(i > (n - 1))
{
break;
}
if(i < current_node)
{
if(min_distance > dmat.at(i).at((n - 1) - current_node))
{
selected_node = ((n - 1) - i);
min_distance = dmat.at(i).at((n - 1) - current_node);
}
}
else
{
if(i == current_node)
{
++i;
if(i > (n - 1))
{
break;
}
}
if(min_distance > dmat.at(current_node).at((n - 1) - i))
{
selected_node = ((n - 1) - i);
min_distance = dmat.at(current_node).at((n - 1) - i);
}
}
}
relaxed_edges.insert((n - 1) - current_node);
current_node = selected_node;
current_distance += sqrt(min_distance);
}
current_distance += sqrt(dmat.at(current_node).at(0));
return current_distance;
}
int main()
{
ifstream input;
string filename = "hw1pr_data.txt";
future<long double> fut = async(best_first, &input, filename);
chrono::milliseconds span(60000);
while((fut.wait_for(span)==future_status::timeout) || input.is_open())
{
}
if(input.is_open())
{
input.close();
}
long double total = fut.get();
tuple<int, int> tempx;
tuple<int, int> tempy;
long int temp;
for(long int i : relaxed_edges)
{
tempx = points.at(temp);
tempy = points.at(i);
cout << get<0>(tempx) << "\t" << get<1>(tempx) << "\t" << get<0>(tempy) << "\t" << get<1>(tempy) << endl;
temp = i;
}
cout << total << endl;
return 0;
}

335
hw1/hw1pr2/hw1pr2.cpp Normal file
View file

@ -0,0 +1,335 @@
// Alexander Huddleston 223000555
// CSCE420
// Due: October 2, 2017 (changed to 4)
// hw1pr2.cpp
// Purpose: Read a file of points, compute interative best-first of a closed path between points.
#include<stdio.h>
#include<iostream>
#include<fstream>
#include<cmath>
#include<future>
#include<chrono>
#include<vector>
#include<climits>
#include<unordered_set>
#include<algorithm>
using namespace std;
// Double vector used to store list of squared distances between points.
vector<vector<long int>> dmat;
// Used to store the points from file.
vector<tuple<int, int>> points;
// Used to store the paths each iteration has traveled.
vector<unordered_set<long int>> relaxed_edges;
// Used to store the distance values of the respective paths.
vector<long int> shortest_paths;
void store_points(ifstream *input, string filename)
{
input->open(filename);
string line = "";
string token = "";
tuple<int, int> temp_point;
get<0>(temp_point) = 0.0;
get<1>(temp_point) = 0.0;
while(getline(*input, line))
{
for(char c : line)
{
if(c == ' ')
{
get<0>(temp_point) = stof(token);
token = "";
}
else
{
token = token + c;
}
}
get<1>(temp_point) = stof(token);
token = "";
points.push_back(temp_point);
}
input->close();
}
void store_distances()
{
long int d1 = 0.0;
long int d2 = 0.0;
tuple< int, int> x;
tuple< int, int> y;
get<0>(x) = 0.0;
get<1>(x) = 0.0;
get<0>(y) = 0.0;
get<1>(y) = 0.0;
vector<long int> tempvec;
for(int r = points.size() - 1; r >= 0; --r)
{
for(int c = 0; c < points.size() - (points.size() - r); ++c)
{
x = points.at(r);
y = points.at(c);
d1 = (get<0>(x) - get<0>(y));
d2 = (get<1>(x) - get<1>(y));
tempvec.push_back(d1*d1 + d2*d2);
}
dmat.push_back(tempvec);
tempvec.clear();
}
}
bool tuple_sort(tuple<long int, long int> t1, tuple<long int, long int> t2)
{
return (get<1>(t1) < get<1>(t2));
}
tuple<vector<int>, long double> iterate_path(int p)
{
// Find best-first shortest path for this iteration.
// Small optomization so we don't have to call points.size() so much.
long int n = points.size();
// In this variation, I want to keep track of the 4 closest points to root.
vector<int> closest;
vector<tuple<long int, long int>> first;
long int temp_counter = n - 1;
if(dmat.at(p).size() > 0)
{
for(long int b : dmat.at(p))
{
tuple<long int, long int> t (temp_counter, b);
first.push_back(t);
--temp_counter;
}
}
for(int a = 0; a < (temp_counter); ++a)
{
tuple<long int, long int> t ((temp_counter - a), (dmat.at(a).at((n - 1) - p)));
first.push_back(t);
}
sort(first.begin(), first.end(), tuple_sort);
temp_counter = 0;
for(tuple<long int, long int> te : first)
{
if(temp_counter > 3)
{
break;
}
closest.push_back(get<0>(te));
++temp_counter;
}
// Store distance up to this point.
long double current_distance = 0;
// Using this to keep track of selected node.
long int current_node = 0;
long int selected_node = 0;
// Using this to keep track of min distance.
long int min_distance = 0;
while(relaxed_edges.at(p).size() < (n - 1))
{
min_distance = INT_MAX;
for(int i = 0; i < (n - 1); ++i)
{
while(relaxed_edges.at(p).find(i) != relaxed_edges.at(p).end())
{
++i;
if(i == current_node)
{
++i;
}
}
if(i > (n - 1))
{
break;
}
if(i < current_node)
{
if(min_distance > dmat.at(i).at((n - 1) - current_node))
{
selected_node = ((n - 1) - i);
min_distance = dmat.at(i).at((n - 1) - current_node);
}
}
else
{
if(i == current_node)
{
++i;
if(i > (n - 1))
{
break;
}
}
if(min_distance > dmat.at(current_node).at((n - 1) - i))
{
selected_node = ((n - 1) - i);
min_distance = dmat.at(current_node).at((n - 1) - i);
}
}
}
relaxed_edges.at(p).insert((n - 1) - current_node);
current_node = selected_node;
current_distance += sqrt(min_distance);
}
current_distance += sqrt(dmat.at(current_node).at(0));
tuple<vector<int>, long double> output;
get<0>(output) = closest;
get<1>(output) = current_distance;
return output;
}
long double best_first(ifstream *input, string filename)
{
// First, store the points from the file into global vector.
store_points(input, filename);
// Store squared distances into dmat.
// Ignore duplicate distances, 0 vectors.
store_distances();
// This is how we know depth.
long int depth = 1;
// Which node iteration are we on?
int n = 0;
unordered_set<long int> empty;
relaxed_edges.push_back(empty);
while(depth < points.size() - 1)
{
// Find shortest path with given path.
tuple<vector<int>, long double> ip = iterate_path(n);
shortest_paths.push_back(get<1>(ip));
vector<int> closest = get<0>(ip);
unordered_set<long int> one;
unordered_set<long int> two;
unordered_set<long int> three;
unordered_set<long int> four;
long int temp = 0;
for(long int i : relaxed_edges.at(n))
{
++temp;
one.insert(i);
two.insert(i);
three.insert(i);
four.insert(i);
if(temp == depth)
{
if(closest.size() > 0)
{
one.insert(closest.at(0));
}
if(closest.size() > 1)
{
two.insert(closest.at(1));
}
if(closest.size() > 2)
{
three.insert(closest.at(2));
}
if(closest.size() > 3)
{
four.insert(closest.at(3));
}
break;
}
}
relaxed_edges.push_back(one);
relaxed_edges.push_back(two);
relaxed_edges.push_back(three);
relaxed_edges.push_back(four);
if(n <= 1)
{
depth = 2;
}
else
{
depth = 2 + ((int)(log(n + 1)/log(4)));
}
++n;
}
return shortest_paths.at(0);
}
int main()
{
ifstream input;
string filename = "hw1pr2_data.txt";
future<long double> fut = async(best_first, &input, filename);
chrono::milliseconds span(60000);
while((fut.wait_for(span)==future_status::timeout) || input.is_open())
{
}
if(input.is_open())
{
input.close();
}
long double total = fut.get();
tuple<int, int> tempx;
tuple<int, int> tempy;
long int temp = 0;
// Change 0 to shortest path.
for(long int i : relaxed_edges.at(0))
{
tempx = points.at(temp);
tempy = points.at(i);
cout << get<0>(tempx) << "\t" << get<1>(tempx) << "\t" << get<0>(tempy) << "\t" << get<1>(tempy) << endl;
temp = i;
}
cout << total << endl;
return 0;
}

View file

@ -0,0 +1,4 @@
0 0
0 1
1 1
1 2

5
hw1/hw1pr2/makefile Normal file
View file

@ -0,0 +1,5 @@
all: main.o
main.o: hw1pr2.cpp
g++ -std=c++17 -lpthread hw1pr2.cpp -o hw1pr2
clean:
rm -rf *.o hw1pr2

4
hw1/hw1pr2_data.txt Normal file
View file

@ -0,0 +1,4 @@
0 0
0 1
1 1
1 2

317
hw1/hw1pr3/hw1pr3.cpp Normal file
View file

@ -0,0 +1,317 @@
// Alexander Huddleston 223000555
// CSCE420
// Due: October 2, 2017 (changed to 4)
// hw1pr3.cpp
// Purpose: A breadth-first search program solving a 15-puzzle problem.
#include<iostream>
#include<vector>
#include<queue>
using namespace std;
// I could move this into a separate header file, due to time
// constrains I am keeping it in main for now.
class GameBoard
{
private:
// A string representing the state of the board.
string state = "";
// Which index the blank tile is at.
int blank = 0;
// List of game moves so far.
vector<string> moves;
public:
// Should only be used at the beginning to set initial state.
void setBoardState(string s)
{
state = s;
blank = s.find('a');
}
// Return the current board state.
string getBoardState()
{
return state;
}
// Return the vector of move strings.
vector<string> getMoves()
{
return moves;
}
// Change board state, make move. Not necessarily in that order.
void swap(char c)
{
char temp = 'p';
switch(c)
{
case 'l':
temp = state[blank - 1];
state[blank - 1] = 'a';
state[blank] = temp;
blank = --blank;
break;
case 'r':
temp = state[blank + 1];
state[blank + 1] = 'a';
state[blank] = temp;
blank = ++blank;
break;
case 'u':
temp = state[blank - 4];
state[blank - 4] = 'a';
state[blank] = temp;
blank = blank - 4;
break;
case 'd':
temp = state[blank + 4];
state[blank + 4] = 'a';
state[blank] = temp;
blank = blank + 4;
break;
default:
break;
}
// Debugging
//print_move(c, state);
moves.push_back(c + state);
}
// Check if a move is legal.
bool isLegal(char c)
{
if(c == 'l')
{
return ((blank % 4) > 0);
}
if(c == 'r')
{
return ((blank % 4) < 3);
}
if(c == 'u')
{
return (blank > 3);
}
if(c == 'd')
{
return (blank < 12);
}
}
// Check if we have solved the puzzle
bool isSolved(string s)
{
if(moves.size() > 0)
{
return !(moves[moves.size() - 1].substr(1).compare(s));
}
else
{
return !(state.compare(s));
}
}
// Useful if we want the previous board state back.
void resetLastMove()
{
if(moves.size() > 0)
{
moves.pop_back();
moves.pop_back();
}
else
{
cerr << "Nothing to reset." << endl;
}
}
} gb;
// Global GameBoard queue.
queue<GameBoard> gbq;
string get_input_game_board()
{
string input = "";
getline(cin, input);
string output = "";
string token = "";
for(char c : input)
{
if(c == ',')
{
output += (char)(stoi(token) + 97);
token = "";
continue;
}
else
{
token += c;
}
}
output += (char)(stoi(token) + 97);
return output;
}
void print_move(char m, string gb)
{
string move = "";
switch(m)
{
case 'l':
move = "Left";
break;
case 'r':
move = "Right";
break;
case 'u':
move = "Up";
break;
case 'd':
move = "Down";
break;
default:
move = "Start";
break;
}
for(int x = 0; x < 16; ++x)
{
if(x == 0)
{
cout << "\t" << move << "\t";
}
else if(x % 4 == 0)
{
cout << "\n\t\t";
}
if(((int)gb[x]) - 97 < 10)
{
cout << ((int)gb[x] - 97) << " ";
}
else
{
cout << ((int)gb[x] - 97) << " ";
}
}
if(m == 's')
{
cout << "\nSwap the blank\n";
}
else
{
cout << "\n\n";
}
}
GameBoard solve_game(GameBoard gb, string solved)
{
gbq.pop();
if(gb.isSolved(solved))
{
return gb;
}
if(gb.isLegal('l'))
{
gb.swap('l');
gbq.push(gb);
if(gb.isSolved(solved))
{
return gb;
}
else
{
gb.swap('r');
gb.resetLastMove();
}
}
if(gb.isLegal('r'))
{
gb.swap('r');
gbq.push(gb);
if(gb.isSolved(solved))
{
return gb;
}
else
{
gb.swap('l');
gb.resetLastMove();
}
}
if(gb.isLegal('u'))
{
gb.swap('u');
gbq.push(gb);
if(gb.isSolved(solved))
{
return gb;
}
else
{
gb.swap('d');
gb.resetLastMove();
}
}
if(gb.isLegal('d'))
{
gb.swap('d');
gbq.push(gb);
if(gb.isSolved(solved))
{
return gb;
}
else
{
gb.swap('u');
gb.resetLastMove();
}
}
return solve_game(gbq.front(), solved);
}
int main()
{
// Initializing with simple test case just in case something goes wrong.
string solved = "bcdefghijklmnopa";
string init = "bcdefghijkalnopm";
// Getting input.
cout << "Enter 15-puzzle starting state by rows (0 for blank):" << endl;
init = get_input_game_board();
cout << "Enter ending state by rows (0 for blank):" << endl;
solved = get_input_game_board();
// Push starting board into queue, start recursion.
gb.setBoardState(init);
gbq.push(gb);
gb = solve_game(gbq.front(), solved);
// Print the solution.
cout << "Solution:" << endl;
print_move('s', init);
if(gb.getMoves().size() > 0)
{
for(string m : gb.getMoves())
{
char c = m[0];
string state = m.substr(1);
print_move(c, state);
}
}
// I added various pieces of code to help the program
// if the user decides to put in an already solved puzzle.
if(gb.getMoves().size() > 0)
{
cout << "Done!\tGenerated " << gb.getMoves().size() << " states." << endl;
}
else
{
cout << "You gave me a solved puzzle." << endl;
}
return 0;
}

5
hw1/hw1pr3/makefile Normal file
View file

@ -0,0 +1,5 @@
all: main.o
main.o: hw1pr3.cpp
g++ -std=c++17 hw1pr3.cpp -o hw1pr3
clean:
rm -rf *.o hw1pr3

110
hw2/420hw2-17fall.txt Normal file
View file

@ -0,0 +1,110 @@
(Print this page as a cover sheet for your printouts)
CSCE 420 HOMEWORK 2
Dr. Daugherity
Due: 11:59 P.M. Monday, October 30, 2017
"On my honor, as an Aggie, I have neither given nor received any unauthorized
aid on any portion of the academic work included in this assignment."
________________________________ ________________________________
Typed or printed name of student Signature of student
NOTE: Please follow your lab instructor's directions for submitting your
assignment through CSNET. ONLY ASSIGNMENTS SUBMITTED TO CSNET WILL BE GRADED!
Make a printout of each source file and staple it behind this cover sheet.
Sign it and turn it in in class Tuesday. IF YOU DO NOT TURN IN A SIGNED COVER
SHEET YOUR WORK WILL NOT BE GRADED!
NOTE: Homework will be graded on build.tamu.edu, using g++ 7.2.0 with
-std=c++17, or javac and java, or python3.
You are free to develop your programs on any other platform, but it is your
responsibility to make sure your programs also compile and execute correctly on
build.tamu.edu as specified.
NOTE: Each file submitted (hw2pr1.cpp, etc.--see below) must begin as follows:
//Your name and UIN
//CSCE 420
//Due: Ocotber 2, 2017
//hw2pr1.cpp (or whatever this file name is)
NOTE: Also write a README.txt file with whatever information is needed to
compile and run your programs. Zip the README.txt and the homework files into
a single file named hw2.zip and submit to CSNET.
The grade for this lab will be based on style (formatting, variable names,
comments, etc.), syntax (no compilation or link errors), and correctness
(passes all test cases). Your grade for this lab is:
Problem # 1 2 3 4
Style /2 /4 /4 /2
Syntax /3 /6 /6 /3
Correctness /5 /10 /10 /5
-------------------------------------------------------------------
Total /10 /20 /20 /10
Grand total _____/50
1. (10 points) Code the mutually-recursive max_value and min_value functions
specified in Figure 5.3 and use them to find the max (root's value)
of a tree read in from the keyboard as a nested list. For example, the tree in Figure 5.2 would be input as
((3,12,8),(2,4,6),(14,5,2))
Name your program hw2pr1.cpp, etc.
2. (20 points) Modify problem 1 to do both alpha and beta pruning according to
Figure 5.7 and print a message "alpha pruning" or "beta pruning" each time that
occurs (in addition to the max of the tree). For example, the tree
((3,8,(7,(3,0,7),(8,8,2))),
(4,(7,9,8),8),
(((3,6,4),2,6),((9,2,9),4,7,(6,4,5) ),4,(6,4,5))
)
would print "alpha pruning" 3 times and "beta pruning" 3 times.
Name your program hw2pr2.cpp, etc.
3. (20 points) Write a Horn clause inference engine which accepts a filename
from the user, reads Horn clauses from that file, and then makes all possible
deductions using forward chaining. The format of the input file will be one
Horn clause per line in PROLOG notation (see section 9.4.2). For example, if
the data file contains
B:-A.
D:-B,C.
A.
C.
then the program will deduce B and D are true. For another test file use
Fig. 7.15.
Name your program hw2pr3.cpp etc. Hint: Fig. 7.14 gives the pseudocode.
OPTIONAL EXTRA CREDIT
=====================
4. (10 points) Write a backtracking prover based on the DPLL_satisfiable
function in Fig. 7.17 which first reads Horn clauses as in the example from
problem 3, then a query preceded by a question mark (that is, what you are
asking to be proven).
B:-A.
D:-B,C.
A.
C.
?D
To prove D is equivalent to saying the Horn clauses entail (imply) D. Since an
implication is only false if the "if" side is true and the "then" side is false,
we add "not D" to the list of Horn clauses and call DPLL_satisfiable. If it
returns false, that means "not not D" must be true, which is D, which is what
we were trying to prove, so output "Proven!" If the query had been E then
adding "not E" and calling DPLL_satisfiable would result in true, so output
"Cannot prove."
Hint: In PROLOG notation "not D" can be written
:-D.
Since the "then" side can always be or'ed with false, this is equivalent to
D --> false
which is equivalent to "not D." Another way of thinking about it is that the
"then" side of a Horn clause is false or'ed with whatever terms are there (in
this case none).
Name your program hw2pr4.cpp etc.