Maintaining a Linked List in File - c++

As a part of the programming Assignment, I have to maintain a linked list in text file. I am pretty convenient with Linked List datastructure, but not so much with files in C++. Can some one give me an idea or overview of how to approach it. I should be able to add or delete the linked list, also able to add or delete the nodes in the linked list or else and should reuse the space that was deleted on one linked list. Each list has a number(integer), all nodes are of same size, contain integer.
My idea would be,
1) maintain a file with numbers(that contain linked List numbers)
0 - NULL
1 - head_offset for_linked_list_num 1
0 - NULL
1 - head_offset_for_linked_list_num 3
1 - head_offset_for_linked_list_num 3
1 - head_offset_for_linked_list_num 3
etc
where -1 is the termiator indication, 1 in a position indicates the ith location has an location associated with it
2) open another file and maintain the linked list like this
data next_offset
data next_offset
data NULL
By doing this, I can keep track of the linked list and efficiently add/delete/display an array.
For doing in C++ what are the functions I need to know and learn. I have very less time and I can code thinking it as an basic level of functions. Please advise. Thanks in advance

1 solution could be to have each list it's own file. The number would be the file name on disk. Inside of the file the first line is always the head node. Each line would be two peices of data. The node data followed by the line in the file for the next node. This would allow you to reuse empty spaces that have been deleted. (a -1 for the next node line would be the end of the list. For example:
1.txt:
(data) (next node lines number)
18 2
32 4
4 -1
5 3
So this link list would be 18 -> 32 -> 5 -> 4

For the what functions to use question, you might consult:
http://www.gnu.org/software/libc/manual/html_node/I_002fO-on-Streams.html#I_002fO-on-Streams
A read through this section may take 15 minutes and covers the basics.

Related

Best way to add only one instance of a number?

I have to create a C++ program that takes in two linked lists and creates a new linked list of nodes from both, but with only one instance of every number. So the output of
list A = 1 --> 3 --> 1 --> 4 and list B = 4 --> 5 --> 12 would be
list C = 1 --> 3 --> 4 --> 5 --> 12. The order of numbers in the new linked list does not matter. What I am having trouble with is how to keep track of each number so that I only add one instance of that number to my new linked list. The only thing I can think is to iterate through the nodes and check if the number is already there. But is there a better way?
Sort each of the two input lists into ascending-order first, then you can just look at the first item at the head of each list, pop the smaller of the two off the head of its list, then append it to the tail of your new list — unless it is equal to the number currently at the tail of your new list, in which case just discard it. Repeat until both input lists are empty.

fstream deleting specific start to end rows

Im a noob programmer currently making a small family database using cpp but i have trouble deleting a family from the the list...
My list looks something like this
start-of-family 1
jim
joe
bob
sam
end-of-family 1
start-of-family 2
rob
max
end-of-family 2
start-of-family 3
sue
tom
kim
end-of-family 3
If i wanted to delete family 1, I would locate start-of-family 1 and end-of-family 1. Then run a loop but how do i locate it if the user only inputs an int to represent a family number. Also how do i make the succeeding family numbers deduct by 1 so that family 2 will be 1 and family 3 will be 2.
thanks a lot
If I were doing this problem I would start by making each family into a vector of names. Then, I would create a vector containing those family vectors.
The result would look something like:
{
<(jim), (joe), (bob), (sam) >
<(rob), (max) >
<(sue), (tom), (kim) >
}
Then, if the user wants to delete one of the families, you can use vector.remove(n) where n is the index of the family to be removed.
This sounds like a school or text book assignment. Have you gotten to vectors yet? Where are the names coming from? Are you hard coding them into the list? Or reading them from a .txt file? What kind of list structure are you storing them in right now?
i realized that clearing the db and updating it with what ive got is way easier than modifying the db and updating my program

Best data structure store sets of numbers from a text file

I have an assignment where I need to find minimum set cover of some points. I want to be able to store each row of numbers in an individual sets but I do not know the best data structure or approach to do this. I have the number of rows there will be. For example, the .txt file will look like this:
1 2 3 4 5 6
5 6 8 9
1 4 7 10
2 5 7 8 11
3 6 9 12
10 11
Is there a way to dynamically create multiple data structures to store each row of numbers? I was thinking something that works like this if it exists:
list<int> myList[6]; // create 6 lists
myList[0].insert(num); // insert numbers into this list
myList[1].insert(num); //insert numbers into the second list
I do not want to individually create lists because in a .txt file, there can be up to 300 sets of numbers.
edit: my main issue is figuring out how to dynamically create some data structure, preferably if it works with std::set_union since it looks useful to my assignment
If you want to control the number of lists programmatically, you can use a std::vector of datasets. So in your case the declaration would be
std::vector<std::list<int>> lists(6);
Adding new, empty lists to the lists set is done by
lists.push_back({}).

An idea as to how to approach a directed graph

I am trying to write a program using a directed graph (which I know about but have never implemented) to simulate a network of transportation.
The user will input a planet name followed by an integer representing the number of total nodes in the graph. The user will then go through each node one by one. They will give it a name give the number of neighbors that node has and then the specific names. The input will look like this.
some_planet 4
node1 2 node2 node3
node2 1 node4
node3 1 node4
node4 1 node1
I then just output which nodes node1 cannot reach. However, I have some questions about implementing this.
1) The big one is storing this stuff. What is an easy way? I thinking about a LinkedList and thought I would link the locations. Then I could pop pointers onto them corresponding to whatever the input is. However, I have no idea how to do the last part.
2) The next big one is searching the graph. I was planning on a recursive depth-first-search . Is there anything wrong with this algorithm that you see? I need to search for every node individually this way though so I will have to increment this. Can I just throw everything in a for loop?
recursive-d-first-search(graph G, node start, node find)
if(start == find)
return true;
else
for every neighbor n of start
success = recursive-d-first-search(graph G, node n, node find);
if(success)
return true;
return false;
I think you just need to use adjacency matrix to store whole graph's connection relation.
in your case, it should be like:
1 2 3 4
1 0 1 1 0
2 0 0 0 1
3 0 0 0 1
4 1 0 0 0
If you use adjacency matrix, I think the breadth-first search may be a good choice, because it's easy to understand and implement. Meanwhile, you need one queue to store next nodes to be checked, and one list to store which nodes have already been checked
For example, you want to check which nodes node1 cannot reach, you just check row 1 and see that it has 2 and 3, and put 2 and 3 to queue. Then check row 2 to see that it has 4, put 2 to list, and put 4 to queue. Then just use a for loop to do the same operation.
In the end, you just need to check which nodes are not in list.
You can also use Boost::Graph if you don't feel like reinventing the wheel...

O(log n) index update and search

I need to keep track of indexes in a large text file. I have been keeping a std::map of indexes and accompanying data as a quick hack. If the user is on character 230,400 in the text, I can display any meta-data for the text.
Now that my maps are getting larger, I'm hitting some speed issues (as expected).
For example, if the text is modified at the beginning, I need to increment the indexes after that position in the map by one, an O(N) operation.
What's a good way to change this to O(log N) complexity? I've been looking at AVL Arrays, which is close.
I'm hoping for O(log n) time for updates and searches. For example, if the user is on character 500,000 in the text array, I want to very quickly find if there is any meta data for that character.
(Forgot to add: The user can add meta data whenever they like)
Easy. Make a binary tree of offsets.
The value of any offset is computed by traversing the tree from the leaf to the root adding offsets any time a node is a right child.
Then if you add text early in the file you only need to update the offsets for nodes which are parents of the offsets that change. That is say you added text before the very first offset, you add the number of characters added to the root node. now one half of your offsets have been corrected. Now traverse to the left child and add the offset again. Now 3/4s of offsets have been updated. Continue traversing left children adding the offset until all the offsets are updated.
#OP:
Say you have a text buffer with 8 characters, and 4 offsets into the odd bytes:
the tree: 5
/ \
3 2
/ \ / \
1 0 0 0
sum of right
children (indices) 1 3 5 7
Now say you inserted 2 bytes at offset 4. Buffer was:
01234567
Now its
0123xx4567
So you modify just nodes that dominate parts of the array that changed. In this case just
the root node needs to be modified.
the tree: 7
/ \
3 2
/ \ / \
1 0 0 0
sum of right
children (indices) 1 3 7 9
The summation rule is walking from leaf to root I sum to myself, the value of my parent if I am that parent's right child.
To find if there is an index at my current location I start at the root and ask is this offset greater smaller than my location. If yes I traverse left and add nothing. If no I traverse right and add the value to my index. If at the end of traversal my value is equal to my index then yes there is an annotation. You can do a similar traverals with a minimum and maximum index to find the node that dominates all the indices in the range, finding all the indices to the text I'm displaying.
Oh.. and this is just a toy example. In reality you need to periodically rebalance the tree otherwise there is a chance that if you keep adding new indices just in one part of the file you will get a tree which is way out of balance, and worst case performance would no longer be O(log2 n) but would be O(n). To keep the tree balanced you would need to implement a balanced binary tree like a "red/black tree". That would guarantee O(log2 n) performance where N is the number of metadatas.
Don't store indices! There's no way to possibly do that and simultaneously have performance better than O(n) - add a character at the beginning of the array and you'll have to increment n - 1 indices, no way around it.
But if you store substring lengths instead, you'd only have to change one per level of tree structure, bringing you up to O(log n). My (untested) solution would be to use a Rope with metadata attached to the nodes - you might need to play around with that a bit, but I think it's a solid foundation.
Hope that helps!