Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Need help on c++Linked list

108 views
Skip to first unread message

Mwater07

unread,
Sep 21, 2017, 9:12:13 PM9/21/17
to
I would like to write a program that stores nonzero elements of 2 different vectors into 2 different linked lists with their indexes. Then would like t to calculate the dot product and displays the result. I am struggling to read in vector values with indexes into a link list. Please advice

#include <iostream>
#include <vector>
using namespace std;

struct node{
int index; /* original index of non-zero array element */
int value ; /* integer non-zero value at index x */
node *next;
};

class linked_list
{
private:
node *head,*tail;
public:
linked_list()
{
head = NULL;
tail = NULL;
}

void create (int x[], int n)
{
link head=0;
for(int i=0; i<n;i++)
head=new node (a[i],head);
}


};


vector<int> x={0,0,7,0,5,0,0,8,0,4};
vector<int> y={0,0,0,5,6,0,0,0,0,5};


int dotproduct() /*Computes the stored nonzero values and returns the result to product*/
{
int product=0;
while(A!=0 && B!=0)
{
if(A->index == B->index)
{
product = product + A->value * B->value;
A=A->next;
B=B->next;

}
else if(A->index < B->index)
{
A=A->next;
}
else
{
B=B->next;
}
}
return product;
}

int main()
{
generate_A_and_B() ;
int r;
r=dotproduct();
cout<<"Dot Product = "<<r<<endl;
return 0;
}

Barry Schwarz

unread,
Sep 22, 2017, 12:34:10 AM9/22/17
to
On Thu, 21 Sep 2017 18:11:43 -0700 (PDT), Mwater07
<mwat...@gmail.com> wrote:

>I would like to write a program that stores nonzero elements of 2 different vectors into 2 different linked lists with their indexes. Then would like t to calculate the dot product and displays the result. I am struggling to read in vector values with indexes into a link list. Please advice

What part are you having trouble with?
You can scan a vector with a simple for loop
for (i = 0; i < vector.size; i++)
{do something with v[i]}
There is a lot of code available showing how to add elements to a
linked list. Google can find examples for you.
Your use of expressions like A-<value and B->next tell us that A and B
have type node*. If you are going to write code, you should include
the declarations and the code to initialize them. Based on the
comments below, you could changed the signature to
int dotproduct(linked_list *p1, linked_list *p2)
and then populate A and B with code similar to
node* A = p1->head;
after making head public, or create a member function called get_head
and use
mode *A = p1->get_head();

> }
> else if(A->index < B->index)
> {
> A=A->next;
> }
> else
> {
> B=B->next;
> }
>}
>return product;
>}
>
>int main()
>{
> generate_A_and_B() ;

Rather than one function to generate both linked lists, I think you
would be better off with
link_list *link_x = new linked_list;
link_list *link_y = new linked_list;
x->head = generate_list(x);
y->head = generate_list(y);

> int r;
> r=dotproduct();

And then call dotproduct with
r =dotproduct(link_x, link_y);

> cout<<"Dot Product = "<<r<<endl;
> return 0;
>}

--
Remove del for email

Jorgen Grahn

unread,
Sep 22, 2017, 4:17:58 AM9/22/17
to
On Fri, 2017-09-22, Mwater07 wrote:

> I would like to write a program that stores nonzero elements of 2
> different vectors into 2 different linked lists with their
> indexes. Then would like t to calculate the dot product and displays
> the result. I am struggling to read in vector values with indexes
> into a link list. Please advice
...
> class linked_list
> {
> private:
> node *head,*tail;
...

Is this a school exercise? It's almost always a bad idea to create
your own linked lists instead of using std::list (and using std::list
is usually a bad idea, too).

Not wanting to invent this particular wheel is one of the main reasons
I write in C++ instead of C.

/Jorgen

--
// Jorgen Grahn <grahn@ Oo o. . .
\X/ snipabacken.se> O o .

Mr Flibble

unread,
Sep 22, 2017, 6:20:00 PM9/22/17
to
On 22/09/2017 09:17, Jorgen Grahn wrote:
[snip]
> Is this a school exercise? It's almost always a bad idea to create
> your own linked lists instead of using std::list (and using std::list
> is usually a bad idea, too).

Using std::list is not usually a bad idea if you usually use std::list
when appropriate to do so.

/Flibble

Juha Nieminen

unread,
Sep 23, 2017, 3:16:11 AM9/23/17
to
Mwater07 <mwat...@gmail.com> wrote:
> class linked_list
> {
> private:
> node *head,*tail;
> public:
> linked_list()
> {
> head = NULL;
> tail = NULL;
> }
>
> void create (int x[], int n)
> {
> link head=0;
> for(int i=0; i<n;i++)
> head=new node (a[i],head);
> }
> };

Not an answer to your actual question, but you really shouldn't
be creating your own dynamically allocated data structures if
you are not going to follow the meticulous requirements to make
it safe. Your linked_list class above is plagued with multitudes
of problems (starting with the fact that you allocate nodes
with 'new' but you don't 'delete' them anywhere. But that's just
the *start* of the problems.)

In general, unless there's a good reason not to, if you want to
use a linked list, use std::list or std::forward_list.

(The only reasons to create your own implementation is as an
exercise in C++, in which case you really, really should follow
the rule of threes (or fours as is the case with C++11), or if
you require a special list that's somehow different from the
standard one (in which case you *also* should follow the rule of
threes as well.))

ruben safir

unread,
Sep 23, 2017, 6:44:29 PM9/23/17
to
On 09/22/2017 12:33 AM, Barry Schwarz wrote:
> for (i = 0; i < vector.size; i++)
> {do something with v[i]}

for(auto x:v )
{ do something with x}


Paul N

unread,
Sep 24, 2017, 5:26:35 PM9/24/17
to
On Friday, September 22, 2017 at 2:12:13 AM UTC+1, Mwater07 wrote:
> I would like to write a program that stores nonzero elements of 2 different vectors into 2 different linked lists with their indexes. Then would like t to calculate the dot product and displays the result. I am struggling to read in vector values with indexes into a link list. Please advice
>
> #include <iostream>
> #include <vector>
> using namespace std;
>
> struct node{
> int index; /* original index of non-zero array element */
> int value ; /* integer non-zero value at index x */
> node *next;
> };
>
> class linked_list
> {
> private:
> node *head,*tail;
> public:
> linked_list()
> {
> head = NULL;
> tail = NULL;
> }
>
> void create (int x[], int n)
> {
> link head=0;
> for(int i=0; i<n;i++)
> head=new node (a[i],head);
> }

I think you have problems here. Firstly, what does "link" mean? Are you simply trying to set head to 0? Also, you don't seem to be supplying enough arguments to the "new node", you want to pass the index i, the value a[i] and head.

While that may get it working - you also said you were only going to store the non-zero values, so you need an "if"; you're throwing away any previous nodes in the list, which might be a bad move and it would certainly be usual to free them; the function doesn't "create" a list as such, it fills it up with the values from a vector so the name is a bit misleading; and you might want to use NULL instead of 0 for consistency with your other code.

Hope that helps.
Paul.

[Snip rest]

asetof...@gmail.com

unread,
Oct 1, 2017, 5:34:08 PM10/1/17
to
I don't know if this is right or even compile, now I see list as this:
#include <iostream.h>

#define u32 unsigned
#define i32 int
#define S sizeof
#define R return
#define F for
#define MM malloc
#define FF free
#define ooo cout

// Nodo generale rNode<T> di tipo T
template<class T> class rNode{
public:
T nd;
rNode* next;
};

//tList: Lista di rNode<T> di tipo T
template<class T> class rList{
public:
rNode<T>* pnd;
u32 sz;
//-----------------------------

//--- costruttori e distruttori
rList():pnd(0),sz(0){}
rList(T* p,u32 s)
{u32 i;
rNode<T>*v,*w;

pnd=0;sz=0;
if(p==0||s==0)
if(s){ooo<<"\nArgomenti del costruttore non buoni\n"; R;}
else R;
if((int)s<0)
{ooo<<"\nArgomenti del costruttore non buoni\n"; R;}
F(i=0;i<s;++i)
{if( (v=(rNode<T>*)MM(S(rNode<T>)))==0 )
{ooo<<"\nErrore memoria non sufficiente\n";
(*this).remove(0);R;
}
if(pnd==0){pnd=v; v->next=0;}
else {w=pnd;pnd=v;v->next=w;}
v->nd=p[s-i-1]; // array pushed reverse i=0=>s-1 ok; i=s-1 =>s-i-1=s-s+1-1=0 ok
++sz;
}
}

~rList()
{rNode<T>*p,*w;
F(p=pnd;p;p=w)
{w=p->next;FF(p);--sz;}
if(sz){ooo<<"\nErrore in size List\n";}
}

//--- funzione accesso array [per accedere all'elemento Lista[i] deve percorre i nodi della lista]
//se indice fuori del range >sz allora exit(1)
//se indice = sz allora alloca un nodo della lista, e aggiorna sz
T& operator[](i32 n)
{rNode<T>*v,*p,*w;
i32 i;
static T r;

if(n<0||n>sz){ooo<<"\nIndice Fuori range\n"; exit(1);R r;}
F(i=0,w=0,p=pnd;i<n&&p;++i,w=p,p=p->next);
if(p)R p->nd;
if( (v=(rNode<T>*)MM(S(rNode<T>)))==0 )
{ooo<<"\nElemento non creato \n";exit(1);R r;}
if(pnd==0){pnd=v;v->next=0;}
else {w->next=v;
v->next=0;
}
++sz;
R v->nd;
}

//--- funzioni elemento
void insert(T& e)
{rNode<T>*v,*p;
if( (v=(rNode<T>*)MM(S(rNode<T>)))==0 ){ooo<<"\nInsert Non Riuscito\n";R;}
if(pnd==0){pnd=v; v->next=0;}
else {p=pnd;pnd=v;v->next=p;}
v->nd=e; ++sz;
}
//--- lista.remove(0) --rimuove ogni elemento della lista
// lista.remove(&r) --rimuove salva in r l'elemento del nodo puntato da pnd
// elimina tale nodo dalla lista
int remove(T*r)
{rNode<T>*p,*w;
if(r==0) // cancell the list if r==0
{F(p=pnd;p;p=w)
{w=p->next;free(p);--sz;}
if(sz){ooo<<"\nErrore in size List\n";}
R 1;
}
if(pnd==0)R 0;
*r=pnd->nd;
p=pnd->next;
FF(pnd); --sz;
pnd=p;
R 1;
}

void print(void)
{rNode<T>*p;
ooo<<"[";
F(p=pnd;p;)
{ooo<<p->nd;
if(p=p->next)ooo<<", ";
}
ooo<<"] ";
}

// Operatori friend
// moltiplica due liste fino a che la size lo permette
friend T operator*(const rList& a, const rList& b)
{T r=0;
rNode<T>*pa,*pb;

F(pa=a.pnd,pb=b.pnd;pa&&pb;pa=pa->next,pb=pb->next)
r+=(pa->nd)*(pb->nd);
R r;
}

}; //fine classe rList<T>

int mainx(void)
{int i,r;
rList<int> lista;
lista.print();
for(i=0;i<10;++i)
lista.insert(i);
lista.print();
r=lista.remove(&i);
ooo<<"i,r="<<i<<", "<<r<<"\n";
lista.print();
R 0;
}

int main(void)
{int arr[]={0,0,7,0,5,0,0,8,0,4}, r;
int ar1[]={0,0,0,5,6,0,0,0,0,5};
u32 i;
rList<int> la(arr, S arr/S(int));
rList<int> l1(ar1, S ar1/S(int));

ooo<<"la=";la.print();ooo<<"\n";
ooo<<"l1=";l1.print();ooo<<"\n";
r=la*l1;
ooo<<"Result: la*lb="<<r<<"\n";

// try to use vector way la[i], that it is not O(1) as vector and array
F(i=0,ooo<<"la=[";i<la.sz;++i)
ooo<<la[i]<<" ";
ooo<<"]\n";
R 0;
}

/*
Print from main():
la=[0, 0, 7, 0, 5, 0, 0, 8, 0, 4]
l1=[0, 0, 0, 5, 6, 0, 0, 0, 0, 5]
Result: la*lb=50
la=[0 0 7 0 5 0 0 8 0 4 ]
*/

asetof...@gmail.com

unread,
Oct 2, 2017, 2:04:17 AM10/2/17
to
How many errors I had done in that code?

David Brown

unread,
Oct 2, 2017, 2:30:42 AM10/2/17
to
On 02/10/17 08:04, asetof...@gmail.com wrote:
> How many errors I had done in that code?
>

I counted 8 errors, starting with "#define u32" and ending with "#define
ooo".

Actually, make that 10 errors - the mention of "malloc" and "free" in
C++ code is another two errors.

After that, there is no point continuing.

asetof...@gmail.com

unread,
Oct 2, 2017, 2:41:52 AM10/2/17
to
One other error it is i not include <stdlib.h>, it appear C++ compiler and linker know where are malloc / free without warning...
(always if they are right malloc/free)

In C that would be ok with a warning missing prototype

David Brown

unread,
Oct 2, 2017, 3:35:39 AM10/2/17
to
No, in C that would /not/ be okay. Implicit function declarations were
removed in C99.

Barry Schwarz

unread,
Oct 2, 2017, 5:43:01 AM10/2/17
to
On Sun, 1 Oct 2017 14:33:58 -0700 (PDT), asetof...@gmail.com
wrote:

>I don't know if this is right or even compile, now I see list as this:

Then why didn't you try to compile it?

>#include <iostream.h>
>
>#define u32 unsigned
>#define i32 int
>#define S sizeof

The use of these types of macros is so annoying to many contributors
that it almost guarantees you will not get a serious discussion about
the "real" code.

As for me, I just stop reading when I see these abominations.

asetof...@gmail.com

unread,
Oct 2, 2017, 5:59:23 AM10/2/17
to
Barry Schwarz wrote
On Sun, 1 Oct 2017 14:33:58 -0700 (PDT), asetof...@gmail.com
wrote:


>I don't know if this is right or even compile, now I see list as this:


Then why didn't you try to compile it?
--------
I compiled it 2 times

the first with my home made malloc/free/cout input output function library C and C++ (but not all) etc environment (I wrote only a dedicated #include file, one main() that control main() and the command line for compile for using one file library .dll)

The second time using the C and C++ library of the compiler... Both no error or warning compile and run as aspect


Jerry Stuckle

unread,
Oct 2, 2017, 11:16:18 AM10/2/17
to
On 10/2/2017 2:04 AM, asetof...@gmail.com wrote:
> How many errors I had done in that code?
>

If a programmer on one of my projects presented this code, it would
immediately be relegated to the bit bucket. I wouldn't even waste time
with a code review of it.

Besides the comments on the #define statements, your code is almost
impossible to decipher due to the lack of meaningful variable names and
poor structure, i.e.

if(s){ooo<<"\nArgomenti del costruttore non buoni\n"; R;}
else R;

This is a little better:

{if( (v=(rNode<T>*)MM(S(rNode<T>)))==0 )
{ooo<<"\nErrore memoria non sufficiente\n";
(*this).remove(0);R;
}

At least the then clause is in separate lines. But although I've seen
your brace usage before, in my experience it's rather unusual. Most
people I've seen use

if (...) {
then clause
}

Or

if (...)
{
then clause
}

Either way is much easier to read than what you are using.

--
==================
Remove the "x" from my email address
Jerry Stuckle
jstu...@attglobal.net
==================

asetof...@gmail.com

unread,
Oct 2, 2017, 12:02:11 PM10/2/17
to
On put statements and operations in a line:
This is my experience:

Indentation is one art very good
Align code redundancies is good
Multiple instruction for line can be very good too

If operations are correlate
or we are habituated (I don't remember the right word, used) to read/write these operations
As in
for(pa=a.pnd,pb=b.pnd;pa&&pb;pa=pa->next,pb=pb->next)
r+=(pa->nd)*(pb->nd);
one line it is the best indentation
The best layout on the page

For example the just above code can not be seen by me better than in that way without spaces without indentation it is as one single operation for me, clear in what it can do.
If someone say the same in plan English it not will be so clear


Richard

unread,
Oct 2, 2017, 1:26:17 PM10/2/17
to
[Please do not mail me a copy of your followup]

Barry Schwarz <schw...@dqel.com> spake the secret code
<oa24tclb7ee22v9kb...@4ax.com> thusly:

>On Sun, 1 Oct 2017 14:33:58 -0700 (PDT), asetof...@gmail.com
>>#define u32 unsigned
>>#define i32 int
>>#define S sizeof
>
>The use of these types of macros is so annoying to many contributors
>that it almost guarantees you will not get a serious discussion about
>the "real" code.
>
>As for me, I just stop reading when I see these abominations.

Not only are macros like this annoying, they are completely
unnecessary. Just use std::uint32_t from <cstdint> if you really
insist on specifying the size of your integers.

Additionally, your macros are misleading because unsigned/int may not
be 32 bits. The macro for sizeof is just plain obfuscating and serves
no utilitarian purpose.
--
"The Direct3D Graphics Pipeline" free book <http://tinyurl.com/d3d-pipeline>
The Terminals Wiki <http://terminals-wiki.org>
The Computer Graphics Museum <http://computergraphicsmuseum.org>
Legalize Adulthood! (my blog) <http://legalizeadulthood.wordpress.com>

Jerry Stuckle

unread,
Oct 2, 2017, 2:12:01 PM10/2/17
to
On 10/2/2017 12:02 PM, asetof...@gmail.com wrote:
> On put statements and operations in a line:
> This is my experience:
>
> Indentation is one art very good
> Align code redundancies is good
> Multiple instruction for line can be very good too
>

That does not mean your experience is correct - and it definitely is not
the style most experienced C++ programmers use.

> If operations are correlate
> or we are habituated (I don't remember the right word, used) to read/write these operations
> As in
> for(pa=a.pnd,pb=b.pnd;pa&&pb;pa=pa->next,pb=pb->next)
> r+=(pa->nd)*(pb->nd);
> one line it is the best indentation
> The best layout on the page
>
> For example the just above code can not be seen by me better than in that way without spaces without indentation it is as one single operation for me, clear in what it can do.
> If someone say the same in plan English it not will be so clear
>
>

Maybe it can be seen by you better. But most programmers will disagree
with your style. And chances are it would not be allowed on a
multi-programmer project. I wouldn't even allow it in any of the C or
C++ classes I taught.

asetof...@gmail.com

unread,
Oct 3, 2017, 3:35:31 AM10/3/17
to
Perhaps I have to change something because
This
F(i=0,ooo<<"la=[";i<la.sz;++i)
ooo<<la[i]<<" ";
ooo<<"]\n";
should be ok,

But this
F(i=0,ooo<<"la=[";i<=la.sz;++i)
ooo<<la[i]<<" ";
ooo<<"]\n";
Should create one indefinite long linked list (and so ended the memory resource)

Reinhardt Behm

unread,
Oct 3, 2017, 3:48:52 AM10/3/17
to
What does this trash mean?
There is only one reasonable change:
rm *

--
Reinhardt

asetof...@gmail.com

unread,
Oct 7, 2017, 5:39:02 AM10/7/17
to
Possible there are many errors...
#include <iostream.h>
#include <stdlib.h>
#include <time.h>

#define u32 unsigned
#define i32 int
#define S sizeof
#define R return
#define F for
#define MM malloc
#define FF free
#define ooo cout


// Nodo generale rNode<T> di tipo T
template<class T> class rNode{
public:
T nd; // nd: valore del tipo conservato nel nodo
u32 nrd; // nrd: valore associato alla lista a cui appartiene
rNode* next; // puntatore al nodo successivo
rNode* prec; // puntatore al nodo precedente
};

//tList: Linked Lista doppia di rNode<T> di tipo T
template<class T> class rList{
public:
rNode<T>* pnd; // Punta al nodo iniziale per inserimento all'inizio
u32 err; // err=1 allora l'obj e' in errore
u32 rnd; // ogni lista ha il suo valore random per controllare meglio la rimozione o inserimento dopo nodo, di nodi
u32 sz; // size in numero di nodi della lista
static u32 t0; // srand(time(0)) has to be only 1 time;
// at start is t0=0 when the first list is build: srand(time(0)), t0=1, any other list creation use only rand()
// and not srand()
//-----------------------------

//--- costruttori e distruttori

//lista **non inazializzata** e' in stato di errore err=1
//NB: **Qualsiasi operazione di assegnamento cambia lo stato della lista in err=0 [nessun errore]**
rList(){u32 r;pnd=0;err=1;if(t0==0){r=time(0);srand(r);t0=1;}rnd=rand();sz=0;}
rList(T* p,u32 s)
{u32 i, r;
rNode<T>*v,*w;

if(t0==0){r=time(0);srand(r);t0=1;}
pnd=0;err=1;rnd=rand();sz=0;
if(p==0||s==0)
if(s){ooo<<"\nArgomenti del costruttore non buoni\n"; R;}
else R;
if((int)s<0)
{ooo<<"\nArgomenti del costruttore non buoni\n"; R;}
F(i=0;i<s;++i)
{if( (v=(rNode<T>*)MM(S(rNode<T>)))==0 )
{ooo<<"\nErrore memoria non sufficiente\n";
(*this).removeHead(0); R;
}
if(pnd==0){pnd=v;v->next=0;v->prec=0;}
else {w=pnd;pnd=v;
v->next =w;
v->prec =w->prec?w->prec:w;
w->prec =v;
}
v->nd =p[s-i-1]; // array pushed reverse i=0=>s-1 ok; i=s-1 =>s-i-1=s-s+1-1=0 ok
v->nrd=rnd;
++sz;
}
err=0;
}

~rList()
{rNode<T>*p,*w;
u32 led;
F(led=err,p=pnd;p;p=w)
{w=p->next;if(p->nrd==rnd){FF(p);--sz;}else led=1;}
if(sz||(led&&pnd))
{ooo<<"\nErrore distruttore Lista="<<this<<"\n";}
pnd=0;err=0;rnd=0;sz=0;
}

//--- funzione accesso array [per accedere all'elemento Lista[i] deve percorre i nodi della lista]
//se indice fuori del range >=sz allora exit(1)
T& operator[](i32 n)
{rNode<T> *p,*w;
i32 i;
static T r; // the constructor of the type build r as error element for T

if(err) R r;
if(n<0||n>=sz){ooo<<"\nIndice Fuori range\n";R r;} // questo non invalida la lista, r e' l'elemento non inizializzato
F(i=0,w=0,p=pnd;i<n&&p;++i,w=p,p=p->next);
R p->nd;
}

//--- funzioni elemento
void insertHead(T& e)
{rNode<T>*v,*p;

if(err&&pnd){ooo<<"\nInsert Non Riuscito\n"; R;}
if( (v=(rNode<T>*)MM(S(rNode<T>)))==0 )
{err=1;ooo<<"\nInsert Non Riuscito\n";R;}
if(pnd==0){pnd=v;err=0;v->next=0;v->prec=0;}
else {p=pnd;pnd=v;
v->next =p;
v->prec =p->prec?p->prec:p;
p->prec =v;
}
v->nrd=rnd;
v->nd =e; ++sz;
}

//--- lista.removeHead(0) --rimuove ogni elemento della lista, err=1 non inizializata
// lista.removeHead(&r) --salva in r l'elemento del nodo puntato da pnd
// elimina tale nodo dalla lista
int removeHead(T*r)
{rNode<T>*p,*w;
u32 led;

if(r==0) // cancell the list if r==0, even if err=1
{F(led=err,p=pnd;p;p=w)
{w=p->next;if(p->nrd==rnd){FF(p);--sz;}else led=1;}
err=1;
if(sz||(led&&pnd))
{pnd=0;sz=0;ooo<<"\nErrore distruttore Lista="<<this<<"\n";R 0;}
pnd=0;sz=0; // rnd e' lasciato, err=1 perche' la lista non inizializzata
R 1;
}
if(pnd==0||err)R 0;
if(pnd->nrd!=rnd){err=1;R 0;}
*r=pnd->nd;
p=pnd->next;
w=pnd->prec;
if(p->nrd==rnd){FF(pnd);--sz;pnd=p;p->prec=w;}
else {err=1;R 0;}
if(pnd==0&&sz==0)err=1; //lista non inizializzata
if(pnd!=0&&sz==0)err=1; // si e' accorto di un errore
R !err;
}

//--- funzioni insert remove
void insertTail(T& e)
{rNode<T>*v,*p;

if(err&&pnd){ooo<<"\nInsert Non Riuscito\n"; R;}
if( (v=(rNode<T>*)MM(S(rNode<T>)))==0 )
{err=1;ooo<<"\nInsert Non Riuscito\n";R;}
if(pnd==0){pnd=v;err=0;v->next=0;v->prec=0;}
else {p=pnd->prec?pnd->prec:pnd;
// solo un nodo pnd->v p=pnd
// pnd->..->w->v p=w
p->next=v; v->prec=p;
v->next=0;pnd->prec=v;
}
v->nrd=rnd;v->nd=e; ++sz;
}



//--- lista.removeTail(0) --rimuove ogni elemento della lista, err=1 non inizializata
// lista.removeTail(&r) --salva in r l'elemento del nodo puntato da pnd
// elimina tale nodo dalla lista
int removeTail(T*r)
{rNode<T>*p,*w;

if(r==0)R!err;
if(pnd==0||err)R 0;
//pnd->..->w->p
p =pnd->prec?pnd->prec:pnd;
if(p->nrd!=rnd){err=1;R 0;}
w = p->prec;
*r= p->nd;
if(w){ w->next=0;
pnd->prec=w;
}
FF(p);--sz;
if(pnd==0&&sz==0)err=1; //lista non inizializzata
if(pnd!=0&&sz==0)err=1; // si e' accorto di un errore
R !err;
}

int insertAfter(rNode<T>*p, T& a)
{rNode<T>*p,*v,*w;

if((err!=0&&pnd!=0)||(p==0&&pnd!=0)||p->nrd!=rnd)
{ooo<<"\nInsert Non Riuscito\n"; err=1; R 0;}
if(p==0&&pnd==0) R (*this).insertHead(a);
w=p->next;
if(w==0) R (*this).insertTail(a);
if( (v=(rNode<T>*)MM(S(rNode<T>)))==0 )
{err=1;ooo<<"\nInsert Non Riuscito\n"; R 0;}
v->prec=p; v->next=w;p->next=v;w->prec=v;
v->nrd =rnd;v->nd =a; ++sz;
}

void print(void)
{rNode<T>*p;

if(err){ooo<<"[List error]"; R;}
ooo<<"[";
F(p=pnd;p;)
{ooo<<p->nd;
if(p->nrd!=rnd){ooo<<"*"; err=1;}
if(p=p->next)ooo<<", ";
}
ooo<<"] ";
if(err)ooo<<"Trovato errore ";
}

void printRev(void)
{rNode<T>*p;

if(err){ooo<<"[List error]"; R;}
ooo<<"[";
if(pnd)
for(p=pnd->prec;p;)
{ooo<<p->nd;
if(p->nrd!=rnd){ooo<<"*"; err=1;}
if(p==pnd)break;
ooo<<", ";
p=p->prec;
}
ooo<<"] ";
if(err)ooo<<"Trovato errore ";
}

int e(void){R err;}

// Operatori friend
// moltiplica due liste fino a che la size di entrambi lo permette
friend T operator*(const rList& a, const rList& b)
{static T r; //r should be initalizated to err object
rNode<T>*pa,*pb;

if(a.err||b.err)R r;
F(r=0,pa=a.pnd,pb=b.pnd;pa&&pb;pa=pa->next,pb=pb->next)
r+=(pa->nd)*(pb->nd);
R r;
}

}; //fine classe rList<T>

template<class T> u32 rList<T>::t0=0; // sembra che qui si genera lo spazio per l'obj t0


int mainx(void)
{int i,r;
rList<int> lista;

for(i=0;i<10;++i)
lista.insertTail(i);

ooo<<"lista=";lista.print();ooo<<"\n";
ooo<<"lista=";lista.printRev();ooo<<"\n";

r=lista.removeTail(&i);
ooo<<"i,r="<<i<<", "<<r<<"\n";
ooo<<"lista=";lista.print();ooo<<"\n";
ooo<<"lista=";lista.printRev();ooo<<"\n";
R 0;
}

int main(void)
{int arr[]={0,0,7,0,5,0,0,8,0,4}, r;
int ar1[]={0,0,0,5,6,0,0,0,0,5};
u32 i;
rList<int> la(arr, S arr/S(int));
rList<int> l1(ar1, S ar1/S(int));

ooo<<"la=";la.print();ooo<<"\n";
ooo<<"l1=";l1.print();ooo<<"\n";
ooo<<"la=";la.printRev();ooo<<"\n";

r=la*l1;
ooo<<"Result: la*lb="<<r<<"\n";

// try to use vector way [], that it is not O(1) as vector and array
0 new messages