forked from Syntaf/AutoComplete
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathauto.cpp
161 lines (145 loc) · 4.42 KB
/
auto.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
// program structure runs as follows:
// Linux distribution -- ./auto wordList inputFile
// Windows distribution -- auto wordList inputFile
#include <iostream>
#include <limits>
#include <cstdlib>
#include <string>
#include <vector>
#include <fstream>
#include "autoCompleteConfig.h"
#include <queue>
bool openGood(std::ifstream&, char* argv);
void readDictionary(std::ifstream&, std::vector<std::string>&, char* argv);
void readInput(std::ifstream&, std::vector<std::string>&, char* argv);
bool search(std::vector<std::string>&, std::vector<std::string>&,
std::queue<std::string>&);
typedef std::vector<std::string>::iterator vecIter;
int main(int argc, char* argv[])
{
std::ifstream wordFile, inFile;
std::queue<std::string> matchingCase;
std::vector<std::string> dictionary, input;
// cmake build version(as specified in cmake header
std::cout << "VERSION " << MAJOR << "." << MINOR << std::endl;
// if the user enters no args
if(argc == 1) {
std::cout << "Usage: ./auto <wordList> <inputFile>" << std::endl;
return 1;
// testing for retarded user
} else if(argc == 2) {
std::cout << "Error, must provide inputFile" << std::endl;
return 1;
}
// open dictionary text file
if(!openGood(wordFile, argv[1])) {
std::cout << "Error, dictionary file could not be opened\n";
return 1;
}
// now open input file with the words we need to complete
if(!openGood(inFile, argv[2])) {
std::cout << "Error, input file could not be opened\n";
return 1;
}
#ifdef USE_INPUT
readDictionary(wordFile, dictionary, argv[1]);
readInput(inFile, input, argv[2]);
#else
//--------------------------------------------------------------------
input.push_back("par");
dictionary.push_back("apple");
dictionary.push_back("and");
dictionary.push_back("batman");
dictionary.push_back("gone");
dictionary.push_back("imaginary");
dictionary.push_back("parachute");
dictionary.push_back("paraglide");
dictionary.push_back("testing");
dictionary.push_back("zoo");
//--------------------------------------------------------------------
#endif
//check to make sure list is sorted!
//--check, ok done
if(!search(dictionary, input, matchingCase)) {
std::cout << "no words have been found matching...." << std::endl;
return 1;
}
// print contents of queue
while(!matchingCase.empty()) {
//make sure to display our queue in the order we found them
std::cout << matchingCase.front() << std::endl;
//pop off the front of the queue
matchingCase.pop();
}
return 0;
}
// test if file passed to function is valid and can be read
bool openGood(std::ifstream& file, char* argv)
{
file.open(argv);
if (file.is_open()){
std::cout << "File was opened in openGood." << std::endl;
//if file can be opened
return true;
//return true
} if (!file.is_open()){
std::cout << "File could not be opened in openGood." << std::endl;
//file cannot be open
return false;
//return false
} else{
std::cout << "Crash." << std::endl;
return false;
}
}
// read data from file into vector, I feel a vector is much more
// optimized for standard data types than say, a linked list. open
// for debate though, a hash table might also be a viable data structure
void readDictionary(std::ifstream& inFile, std::vector<std::string>& vec, char* argv)
{
std::string line;
inFile >> line;
vec.push_back(line);
while(inFile) {
inFile >> line;
vec.push_back(line);
}
}
//same as read dictionary, but for our input file
void readInput(std::ifstream& inFile, std::vector<std::string> &vec, char* argv)
{
std::string line;
inFile >> line;
vec.push_back(line);
while(inFile){
inFile >> line;
vec.push_back(line);
}
}
//search function uses a binary search algorithm on a given vector. It is important
//to note that the string MUST be sorted before being passed into binary search
//or you are going to have a very bad time. Currently only finds one word but must
//be developed to catch all similar words
bool search(std::vector<std::string>& dict, std::vector<std::string>& in,
std::queue<std::string>& out)
{
int first=0, last= dict.size() -1;
while(first <= last)
{
int middle = (first+last)/2;
std::string sub = (dict.at(middle)).substr(0,in.at(0).length());
int comp = (in.at(0)).compare(sub);
//if comp returns 0(found word matching case)
if(comp == 0){
out.push(dict.at(middle));
return true;
}
//if not, take top half
else if (comp > 0)
first = middle + 1;
//else go with the lower half
else
last = middle - 1;
}
return false;
}