MSXML2: How can I get text of a node if any child node in between parent node? - msxml

I have this node:
MSXML2::IXMLDOMNodePtr node;
node->Getxml() returns "<para>this is sample para which has newline<b/>coming</para>"
but when i use node->Gettext(); it returns
this is sample para which has newlinecoming
I want get this as
"this is sample para which has newline\ncoming"
here <b/> represent newline.
List item
How can I get this newline character inserted?

Related

Travelling through maze recursively & inserting nodes in all spaces

I have a maze program that takes 5 mazes and inserts nodes into the outlines of those mazes. I'm creating a directed graph that can represent the freespaces in the maze by placing a graph node at each free space grid location and connecting them together with edges.
I'm stuck on a function that actually involves filling the freespaces of the maze with nodes and connecting them. The nodes don't need to follow a certain pattern at the moment, they just need to fill up all empty space like the images shown below. My program right now just displays a blank maze with no nodes.
I'm given a set of guidelines which are commented in computeGraph(), but I am really stumped as to how I would trace a maze recursively. My code under the function is gibberish and doesn't do anything. I'm really lost as to what to do and would appreciate some help or guidance. I'm not asking for anything else in the program to be touched, only computeGraph() as it's my problem right now. Also I should mention that I'm not allowed to create any extra arrays for this task which makes the problem even harder.
If the comments are not enough, basically the function's purpose is to allocate space for the new graph and return it. Each node of the graph must be dynamically-allocated and connected by setting the appropriate Node up/down/left/right pointers.
Thanks again for any help. I can post the full code/all the files for the program if required, but I just posted only what I thought was necessary for this particular problem.
maze.c:
#include <stdio.h>
#include <stdlib.h>
#include "graphSet.h"
#include "mazeDisplay.h"
// Compute the graph for the given maze and add it to the given graph set.
Graph *computeGraph(char maze[HEIGHT][WIDTH]) {
// Create the initially-empty graph
int i, j;
for(i = 0; i < HEIGHT; i++){
for(j = 0; j < WIDTH; j++){
maze[i][j] = '\0';
}
}
// Find a starting node, then trace out the maze recursively. A starting node can be
// found by searching from top to bottom, left to right, for a non-wall maze location.
// You MUST NOT hard-code this start location ... it must be determined by your code.
Node *newNode;
Node *currNode;
Node *prevNode;
currNode = *rootNode;
currPos[0][0];
prevNode = NULL;
while(currNode != NULL){
if(currPos[0][0] == maze[x][y]){
break;
}
prevNode = currNode;
}
newNode = malloc(sizeof(Node));
if(prevNode->up != 1){
prevNode->up = newNode;
}else if(prevNode->down != 1){
prevNode->down = newNode;
}else if(prevNode->left != 1){
prevNode->left = newNode;
}else if(prevNode->right != 1){
prevNode->right = newNode;
}
// To trace out the maze recursively, you will likely want to create a recursive
// procedure that is called by this one. It should take parameters to indicate
// the location in the maze to start tracing from, the maze itself and also the node
// that led to this node (i.e., the previous one in the tree that led here). If you
// start with the root node, then the previous node should be NULL.
//
// As you go through the maze, make sure to mark off maze locations that you have
// visited (perhaps by putting a '2' character at that location) so that you do not
// go back to that location again and end up with infinite recursion. So you can
// stop the recursion when you reach a wall (i.e., a '1' character in the maze) or a
// '2' character. A '0' character means that it is a free space that you just arrived
// at for the first time. Make sure to check recursively in all directions. In my
// solutions (shown on the assignment), I used an ordering of up/down/left/right. So
// if you want solutions to look like mine, you should follow that ordering as well.
//
// As you traverse the maze, make sure to connect the previous node to the current one.
// You'll have to check which direction you can from (i.e., x and y values) so that
// you know whether it is the up/down/left or right pointer to set.
}
// This procedure must clean up graph by removing all nodes in which the previous and
// next nodes have the same x or y value as it.
void cleanUpGraph(Node *n, Node *previousNode) {
}
// This is where it all begins
int main() {
char mazes[5][HEIGHT][WIDTH] = {
{"111111111111111111111",
"100000001000100000001",
"101111111010111011111",
"100000000010000010001",
"101110111111101110111",
"100010001000000000001",
"111011111111111110111",
"101010001000100000001",
"101110111011101011101",
"100010000000001010001",
"101010111011111111111",
"101000001000100000001",
"101111111110101111101",
"100010100000100000101",
"111110101110101111101",
"100010001000000010101",
"101010111111111010111",
"101010001000000010001",
"101111111010111011101",
"100000000010001000001",
"111111111111111111111"},
{"111111111111111111111",
"100000000000000000001",
"101111111111111111111",
"100000000000000000001",
"101111111111111111111",
"100000000000000000001",
"111111111111111111101",
"100000000000000000001",
"101111111111111111111",
"100000000000000000001",
"111111111111111111101",
"100000000000000000001",
"101111111111111111111",
"101111111111111111101",
"101111111111111111101",
"101000100010001000101",
"101010101010101010101",
"101010101010101010101",
"101010101010101010101",
"100010001000100010001",
"111111111111111111111"},
{"111111111111111111111",
"100000000000000000001",
"101010101010101010101",
"100000000000000000001",
"101110111011101110111",
"100000000000000000001",
"101111101111101111101",
"100000000000000000001",
"101111111001111111101",
"100000000000000000001",
"101111111111111111101",
"100111111111111111001",
"100011111111111110001",
"100001111111111100001",
"100000111111111000001",
"100000011111110000001",
"100000001111100000001",
"100000000111000000001",
"100000000010000000001",
"100000000000000000001",
"111111111111111111111"},
{"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111110111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111",
"111111111111111111111"},
{"111111111111111111111",
"111100000000000000001",
"111000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"100000000000000000001",
"111111111111111111111"}};
// Open a display window
openDisplayWindow();
// Allocate a GraphSet to store the graphs for each maze
GraphSet *gSet;
// Compute the graphs for each maze and add them to a Graph Set
for (int i=0; i<5; i++) {
Graph *g = computeGraph(mazes[i]);
// Add g to gSet properly
// ...
}
// Show the graphs
Graph *g; // ... set this to the first graph in gSet ...
for (int i=0; i<5; i++) {
drawMaze(mazes[i]); // Draw the maze
// drawGraph(g->rootNode); // Draw the graph
getchar(); // Wait for user to press enter
// cleanUpGraph(g->rootNode, NULL); // Clean up the graph
// drawMaze(mazes[i]);
// drawGraph(g->rootNode);
// ... get the next graph in the set ...
// ... INSERT A LINE OF CODE HERE ...
getchar(); // Wait again for the user to press ENTER before going on to the next maze
}
// Free up all allocated memory
// ...
// Close the display window
closeDisplayWindow();
}
graphSet.h:
// This struct represents a single intersection/Node in a maze. It keeps track
// of the x(i.e., column) and y (i.e. row) of the intersection in the maze
// as well as the Nodes in all 4 directions around it). NULL is used to
// indicate that no Node is beside it in a particular direction.
typedef struct nd {
int x;
int y;
struct nd *up;
struct nd *down;
struct nd *left;
struct nd *right;
} Node;
// This struct represents a single maze graph
typedef struct gr {
Node *rootNode;
struct gr *nextGraph;
} Graph;
// This struct represents a set of maze graphs
typedef struct {
Graph *firstGraph;
Graph *lastGraph;
} GraphSet;
The mazes as shown can be interpreted as a series of single-square rooms, which are connected by "doors" whereever two empty squares touch.
That way, this problem is simpliefied to an undirected graph of identical rooms.
I just repeat this, though I am convinced that you already arrived at this view yourself.
The goal is hence to visit each room and know when all have been visited.
Then the goal to malloc for each empty space (but not more than once) can be achieved by mallocing only when visiting a square for the first time, which can be guaranteed by using a flag set when visiting a new room, at the same time when mallocing. These flags can be "added" to each room, by mirroring the data structure which stores the "empty"/"wall" info.
The remaining goal is to make sure that each empty square gets visited, as long as it CAN be visited. For that I propose to use the "left hand rule" for maze visiting: "Always leave a room through the exit to left of where you entered." It is basically a traversal for directed graphs, similar to the most widely used traversal for binary trees. I.e. for possible exits to North, East, Sout, West, North, always exit through the "next" exit in this order.
The lefthand rule is only for directed graphs without "loops"/"circles", with is of course NOT applicable to your kind of mazes.
To solve that problem, use the ariadne thread. It is a path through all the already visited rooms. Note that you need a path data structure, a flag for each room is not sufficient to keep track of the ariadne thread.
If while using the left-hand-rule you enter a room you have already visited (i.e. it is already found in the path you travelled), then do not enter it and select the next exit, as if the first selected exit does not exist. Imagine the "door" to be locked there. When you are out of exits to unvisited rooms, go back along the ariadne thread until you again find yet unused exits to yet unvisited rooms.
When you are forced to go back to the first room you visited, then you have visited all rooms.
As described above, you ariadne thread grows longer while returning during the search for unvisited rooms. For more efficient implementation, you can shorten the ariadne thread on your way back and rely on the mirrored flags for "already malloced". I.e. the room to go back to is found in the previous entry of the path, while the decision whether to enter a room can be based on the flag.
In your sample solutions, imagine the red dots to be the flags, while the blue lines represent the (unshortened) ariadne thread, which is everywhere double (on the way in and the way out).
Take pen and paper (with an empty version of the maze).
Play the person walking through the maze, draw the blue ariadne thread. Like that it will be possible to follow the description I provided.
Then program it.

How can I save changes on a dynamic tree on c?

I'm building a database for a project, every entry has an RB-Tree that contains its attributes, but with the function that I made I cannot save the changes of the trees. I create and link the new nodes but when I return the new nodes are lost
x is the attribute (relation) identifier, used to look inside the tree and see if the relation already exists or not. id_orig is the entry of the database which I have to ad the relation to. tree * radice is the root of the tree and tree * nil is the nil pointer (substitute to NULL).
Add_rel_list is the function used to add a new relation after adding it on a new tree node if there isn't one.
insert fixup is used to check that the RB-Tree is balanced and respects it's definition
this is the add attribute function
struct tree *insert(unsigned long int x, char id_orig[50], char nome_relazione[50], struct tree *radice, struct tree * nil){ /*devo creare un nuovo nodo dell'albero */
if(radice==nil){
//this part is used to create a new root of the tree
}
else{
struct tree *newleaf=malloc(sizeof(struct tree)); /*creating a new node*/
//struct rel_list *lista=malloc(sizeof(struct rel_list));
newleaf->codice_rel=x; /*assign the node number*/
//newleaf->rel=lista; //link the list
newleaf->nome_rel=(char*)malloc(strlen(nome_relazione)+1);
strcpy(newleaf->nome_rel, nome_relazione);
newleaf->rel=add_rel_list(newleaf->rel, id_orig); /*helper function to add the list names*/
newleaf->num_rel=1; /*metto a 1 la quantit‡ del tipo di relazioni esistenti*/
struct tree *y= nil;
struct tree *w= radice;
while(w!=nil){
y=w;
if(newleaf->codice_rel<w->codice_rel){
w=w->left;
}
else{
w=w->right;
}
newleaf->prev=y;
if (y==nil){
radice=newleaf; //l'albero Ë vuoto
}
else if(newleaf->codice_rel<y->codice_rel){
if(newleaf->codice_rel<y->left->codice_rel){
newleaf->right=y->left;
}
else{
newleaf->left=y->left;
}
y->left=newleaf;
}
else{
if(newleaf->codice_rel<y->right->codice_rel){
newleaf->right=y->right;
}
else{
newleaf->left=y->right;
}
y->right=newleaf;
}
newleaf->black=0;
insert_fixup(radice, newleaf, nil);
return radice;
}
}
}
struct tree *insert_rel(unsigned long int x, char *id_orig, struct tree *radice, struct tree *nil, char *id_dest, char *nomerel, controllo * controllore){
//non relevant to the problem
return radice;
}
void insert_fixup(struct tree *radice, struct tree* nuovo, struct tree *nil){
//this function is used to balance the tree
}
the function should create a new node and link it inside the tree. the calls that are in the function and that I did not post are irrelevant to the problem, leftrotate and rightrotate are for the manipulation of the RB-Tree. when, later on, I look inside the tree for the attributes (relations) the only one saved is the first one, the root of the tree. using gdb the linking is correct but when I return to the main part of the code I lose all the new nodes of the tree

Strtok is returning (null) after the first token

I'm trying to separate a string read from a file by the token '#'. StrTok separates the first token correctly but when i print what is supposed to be the second token it returns nothing but (null).
I tried to change the format of the file that is being read and using an aux variable to hold the content of strtok(NULL,"#"), but the results dont change.
void ler_fich_cidades(Lista_Cidades cidade,Lista_Pontos pt){
FILE *p;
int file_check=0;
char linha[TAM];
Lista_Pontos ptos;
Cada_cidade city;
char *aux = (char*)malloc(TAM*sizeof(char));
p = fopen("locais.txt", "r");
while(!feof(p)){
fgetstr(linha,sizeof(linha),p); //this function removes any '\n'.It is working,because it is used for other things
strcpy(cidade->nome_cidade,strtok(linha,"#")); //This line is working as intended
printf("%s\n",cidade->nome_cidade);
strcpy(ptos->ponto.nome,strtok(NULL,"#")); //This one is not
printf("%s\n",ptos->ponto.nome); //Printing (null)
}
}
The file being read has the following format:
"#Coimbra"
"#Universidade De Coimbra#E uma das universidades mais antigas do mundo ainda em operaçao, sendo a mais antiga e uma das maiores do pais.#8:00h-18:00h#Segunda,Terca,Quarta,Quinta,Sexta,Sábado"
The output is supposed to be:
Coimbra
Universidade De Coimbra
But the actual output is just:
Coimbra
The problem isn't that strtok is returning NULL. The problem is that you never initialise ptos, so it is pointing into limbo.
Also, your function seems to take an argument pt, but you never use it.

Operation ignoring via pointers in AVL tree

I am building an AVL tree, using this structure:
typedef struct node* nodep;
typedef struct node {
int postal_number;
int h; /* height */
nodep left, right, parent;
} Node;
Everything is working great: rotating, searching and inserting. The problem is with deleting a node. It deletes most of the node, except for few leaves after deleting most of the tree. My delete code (the problematic part) is:
int delete_postal(nodep* t, int in_postal){
nodep to_delete;
nodep* the_parent;
to_delete = search_postal((*t), in_postal);
the_parent = &(to_delete->parent);
/** if the node we want to delete is a leave **/
if (to_delete->right == NULL && to_delete->left == NULL) {
if (to_delete == (*the_parent)->right){ /* the node we want to delete is right son */
(*the_parent)->right = to_delete->right;
else { /* the node we want to delete is left son */
(*the_parent)->left = to_delete->left;
}
I made it so (*the_parent) will be the node himself in the tree, and when debugging it stepping into the if, it acts as if it did the deletion (making the child of the node the child of the node's father - I'm not dealing with malloc right now), but it just does not do it. The father keeps on pointing to the node that I would like to delete and not to NULL.
All the rest of the first deletion (nodes and leaves) works fine with this syntax.
Does somebody know what I am missing?

Traverse tree without recursion and stack in C

How to traverse each node of a tree efficiently without recursion in C (no C++)?
Suppose I have the following node structure of that tree:
struct Node
{
struct Node* next; /* sibling node linked list */
struct Node* parent; /* parent of current node */
struct Node* child; /* first child node */
}
It's not homework.
I prefer depth first.
I prefer no additional data struct needed (such as stack).
I prefer the most efficient way in term of speed (not space).
You can change or add the member of Node struct to store additional information.
If you don't want to have to store anything, and are OK with a depth-first search:
process = TRUE;
while(pNode != null) {
if(process) {
//stuff
}
if(pNode->child != null && process) {
pNode = pNode->child;
process = true;
} else if(pNode->next != null) {
pNode = pNode->next;
process = true;
} else {
pNode = pNode->parent;
process = false;
}
}
Will traverse the tree; process is to keep it from re-hitting parent nodes when it travels back up.
Generally you'll make use of a your own stack data structure which stores a list of nodes (or queue if you want a level order traversal).
You start by pushing any given starting node onto the stack. Then you enter your main loop which continues until the stack is empty. After you pop each node from the stack you push on its next and child nodes if not empty.
This looks like an exercise I did in Engineering school 25 years ago.
I think this is called the tree-envelope algorithm, since it plots the envelope of the tree.
I can't believe it is that simple. I must have made an oblivious mistake somewhere.
Any mistake regardless, I believe the enveloping strategy is correct.
If code is erroneous, just treat it as pseudo-code.
while current node exists{
go down all the way until a leaf is reached;
set current node = leaf node;
visit the node (do whatever needs to be done with the node);
get the next sibling to the current node;
if no node next to the current{
ascend the parentage trail until a higher parent has a next sibling;
}
set current node = found sibling node;
}
The code:
void traverse(Node* node){
while(node!=null){
while (node->child!=null){
node = node->child;
}
visit(node);
node = getNextParent(Node* node);
}
}
/* ascend until reaches a non-null uncle or
* grand-uncle or ... grand-grand...uncle
*/
Node* getNextParent(Node* node){
/* See if a next node exists
* Otherwise, find a parentage node
* that has a next node
*/
while(node->next==null){
node = node->parent;
/* parent node is null means
* tree traversal is completed
*/
if (node==null)
break;
}
node = node->next;
return node;
}
You can use the Pointer Reversal method. The downside is that you need to save some information inside the node, so it can't be used on a const data structure.
You'd have to store it in an iterable list. a basic list with indexes will work. Then you just go from 0 to end looking at the data.
If you want to avoid recursion you need to hold onto a reference of each object within the tree.

Resources