Free cookie consent management tool by TermsFeed Policy Generator

source: trunk/sources/HeuristicLab.ExtLibs/HeuristicLab.ALGLIB/2.5.0/ALGLIB-2.5.0/tsort.cs @ 3839

Last change on this file since 3839 was 3839, checked in by mkommend, 14 years ago

implemented first version of LR (ticket #1012)

File size: 18.1 KB
Line 
1/*************************************************************************
2Copyright 2008 by Sergey Bochkanov (ALGLIB project).
3
4>>> SOURCE LICENSE >>>
5This program is free software; you can redistribute it and/or modify
6it under the terms of the GNU General Public License as published by
7the Free Software Foundation (www.fsf.org); either version 2 of the
8License, or (at your option) any later version.
9
10This program is distributed in the hope that it will be useful,
11but WITHOUT ANY WARRANTY; without even the implied warranty of
12MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13GNU General Public License for more details.
14
15A copy of the GNU General Public License is available at
16http://www.fsf.org/licensing/licenses
17
18>>> END OF LICENSE >>>
19*************************************************************************/
20
21using System;
22
23namespace alglib
24{
25    public class tsort
26    {
27        public static void tagsort(ref double[] a,
28            int n,
29            ref int[] p1,
30            ref int[] p2)
31        {
32            int i = 0;
33            int[] pv = new int[0];
34            int[] vp = new int[0];
35            int lv = 0;
36            int lp = 0;
37            int rv = 0;
38            int rp = 0;
39
40           
41            //
42            // Special cases
43            //
44            if( n<=0 )
45            {
46                return;
47            }
48            if( n==1 )
49            {
50                p1 = new int[0+1];
51                p2 = new int[0+1];
52                p1[0] = 0;
53                p2[0] = 0;
54                return;
55            }
56           
57            //
58            // General case, N>1: prepare permutations table P1
59            //
60            p1 = new int[n-1+1];
61            for(i=0; i<=n-1; i++)
62            {
63                p1[i] = i;
64            }
65           
66            //
67            // General case, N>1: sort, update P1
68            //
69            tagsortfasti(ref a, ref p1, n);
70           
71            //
72            // General case, N>1: fill permutations table P2
73            //
74            // To fill P2 we maintain two arrays:
75            // * PV, Position(Value). PV[i] contains position of I-th key at the moment
76            // * VP, Value(Position). VP[i] contains key which has position I at the moment
77            //
78            // At each step we making permutation of two items:
79            //   Left, which is given by position/value pair LP/LV
80            //   and Right, which is given by RP/RV
81            // and updating PV[] and VP[] correspondingly.
82            //
83            pv = new int[n-1+1];
84            vp = new int[n-1+1];
85            p2 = new int[n-1+1];
86            for(i=0; i<=n-1; i++)
87            {
88                pv[i] = i;
89                vp[i] = i;
90            }
91            for(i=0; i<=n-1; i++)
92            {
93               
94                //
95                // calculate LP, LV, RP, RV
96                //
97                lp = i;
98                lv = vp[lp];
99                rv = p1[i];
100                rp = pv[rv];
101               
102                //
103                // Fill P2
104                //
105                p2[i] = rp;
106               
107                //
108                // update PV and VP
109                //
110                vp[lp] = rv;
111                vp[rp] = lv;
112                pv[lv] = rp;
113                pv[rv] = lp;
114            }
115        }
116
117
118        public static void tagsortfasti(ref double[] a,
119            ref int[] b,
120            int n)
121        {
122            int i = 0;
123            int k = 0;
124            int t = 0;
125            double tmp = 0;
126            int tmpi = 0;
127
128           
129            //
130            // Special cases
131            //
132            if( n<=1 )
133            {
134                return;
135            }
136           
137            //
138            // General case, N>1: sort, update B
139            //
140            i = 2;
141            do
142            {
143                t = i;
144                while( t!=1 )
145                {
146                    k = t/2;
147                    if( (double)(a[k-1])>=(double)(a[t-1]) )
148                    {
149                        t = 1;
150                    }
151                    else
152                    {
153                        tmp = a[k-1];
154                        a[k-1] = a[t-1];
155                        a[t-1] = tmp;
156                        tmpi = b[k-1];
157                        b[k-1] = b[t-1];
158                        b[t-1] = tmpi;
159                        t = k;
160                    }
161                }
162                i = i+1;
163            }
164            while( i<=n );
165            i = n-1;
166            do
167            {
168                tmp = a[i];
169                a[i] = a[0];
170                a[0] = tmp;
171                tmpi = b[i];
172                b[i] = b[0];
173                b[0] = tmpi;
174                t = 1;
175                while( t!=0 )
176                {
177                    k = 2*t;
178                    if( k>i )
179                    {
180                        t = 0;
181                    }
182                    else
183                    {
184                        if( k<i )
185                        {
186                            if( (double)(a[k])>(double)(a[k-1]) )
187                            {
188                                k = k+1;
189                            }
190                        }
191                        if( (double)(a[t-1])>=(double)(a[k-1]) )
192                        {
193                            t = 0;
194                        }
195                        else
196                        {
197                            tmp = a[k-1];
198                            a[k-1] = a[t-1];
199                            a[t-1] = tmp;
200                            tmpi = b[k-1];
201                            b[k-1] = b[t-1];
202                            b[t-1] = tmpi;
203                            t = k;
204                        }
205                    }
206                }
207                i = i-1;
208            }
209            while( i>=1 );
210        }
211
212
213        public static void tagsortfastr(ref double[] a,
214            ref double[] b,
215            int n)
216        {
217            int i = 0;
218            int k = 0;
219            int t = 0;
220            double tmp = 0;
221            double tmpr = 0;
222
223           
224            //
225            // Special cases
226            //
227            if( n<=1 )
228            {
229                return;
230            }
231           
232            //
233            // General case, N>1: sort, update B
234            //
235            i = 2;
236            do
237            {
238                t = i;
239                while( t!=1 )
240                {
241                    k = t/2;
242                    if( (double)(a[k-1])>=(double)(a[t-1]) )
243                    {
244                        t = 1;
245                    }
246                    else
247                    {
248                        tmp = a[k-1];
249                        a[k-1] = a[t-1];
250                        a[t-1] = tmp;
251                        tmpr = b[k-1];
252                        b[k-1] = b[t-1];
253                        b[t-1] = tmpr;
254                        t = k;
255                    }
256                }
257                i = i+1;
258            }
259            while( i<=n );
260            i = n-1;
261            do
262            {
263                tmp = a[i];
264                a[i] = a[0];
265                a[0] = tmp;
266                tmpr = b[i];
267                b[i] = b[0];
268                b[0] = tmpr;
269                t = 1;
270                while( t!=0 )
271                {
272                    k = 2*t;
273                    if( k>i )
274                    {
275                        t = 0;
276                    }
277                    else
278                    {
279                        if( k<i )
280                        {
281                            if( (double)(a[k])>(double)(a[k-1]) )
282                            {
283                                k = k+1;
284                            }
285                        }
286                        if( (double)(a[t-1])>=(double)(a[k-1]) )
287                        {
288                            t = 0;
289                        }
290                        else
291                        {
292                            tmp = a[k-1];
293                            a[k-1] = a[t-1];
294                            a[t-1] = tmp;
295                            tmpr = b[k-1];
296                            b[k-1] = b[t-1];
297                            b[t-1] = tmpr;
298                            t = k;
299                        }
300                    }
301                }
302                i = i-1;
303            }
304            while( i>=1 );
305        }
306
307
308        public static void tagsortfast(ref double[] a,
309            int n)
310        {
311            int i = 0;
312            int k = 0;
313            int t = 0;
314            double tmp = 0;
315
316           
317            //
318            // Special cases
319            //
320            if( n<=1 )
321            {
322                return;
323            }
324           
325            //
326            // General case, N>1: sort, update B
327            //
328            i = 2;
329            do
330            {
331                t = i;
332                while( t!=1 )
333                {
334                    k = t/2;
335                    if( (double)(a[k-1])>=(double)(a[t-1]) )
336                    {
337                        t = 1;
338                    }
339                    else
340                    {
341                        tmp = a[k-1];
342                        a[k-1] = a[t-1];
343                        a[t-1] = tmp;
344                        t = k;
345                    }
346                }
347                i = i+1;
348            }
349            while( i<=n );
350            i = n-1;
351            do
352            {
353                tmp = a[i];
354                a[i] = a[0];
355                a[0] = tmp;
356                t = 1;
357                while( t!=0 )
358                {
359                    k = 2*t;
360                    if( k>i )
361                    {
362                        t = 0;
363                    }
364                    else
365                    {
366                        if( k<i )
367                        {
368                            if( (double)(a[k])>(double)(a[k-1]) )
369                            {
370                                k = k+1;
371                            }
372                        }
373                        if( (double)(a[t-1])>=(double)(a[k-1]) )
374                        {
375                            t = 0;
376                        }
377                        else
378                        {
379                            tmp = a[k-1];
380                            a[k-1] = a[t-1];
381                            a[t-1] = tmp;
382                            t = k;
383                        }
384                    }
385                }
386                i = i-1;
387            }
388            while( i>=1 );
389        }
390
391
392        /*************************************************************************
393        Heap operations: adds element to the heap
394
395        PARAMETERS:
396            A       -   heap itself, must be at least array[0..N]
397            B       -   array of integer tags, which are updated according to
398                        permutations in the heap
399            N       -   size of the heap (without new element).
400                        updated on output
401            VA      -   value of the element being added
402            VB      -   value of the tag
403
404          -- ALGLIB --
405             Copyright 28.02.2010 by Bochkanov Sergey
406        *************************************************************************/
407        public static void tagheappushi(ref double[] a,
408            ref int[] b,
409            ref int n,
410            double va,
411            int vb)
412        {
413            int j = 0;
414            int k = 0;
415            double v = 0;
416
417            if( n<0 )
418            {
419                return;
420            }
421           
422            //
423            // N=0 is a special case
424            //
425            if( n==0 )
426            {
427                a[0] = va;
428                b[0] = vb;
429                n = n+1;
430                return;
431            }
432           
433            //
434            // add current point to the heap
435            // (add to the bottom, then move up)
436            //
437            // we don't write point to the heap
438            // until its final position is determined
439            // (it allow us to reduce number of array access operations)
440            //
441            j = n;
442            n = n+1;
443            while( j>0 )
444            {
445                k = (j-1)/2;
446                v = a[k];
447                if( (double)(v)<(double)(va) )
448                {
449                   
450                    //
451                    // swap with higher element
452                    //
453                    a[j] = v;
454                    b[j] = b[k];
455                    j = k;
456                }
457                else
458                {
459                   
460                    //
461                    // element in its place. terminate.
462                    //
463                    break;
464                }
465            }
466            a[j] = va;
467            b[j] = vb;
468        }
469
470
471        /*************************************************************************
472        Heap operations: replaces top element with new element
473        (which is moved down)
474
475        PARAMETERS:
476            A       -   heap itself, must be at least array[0..N-1]
477            B       -   array of integer tags, which are updated according to
478                        permutations in the heap
479            N       -   size of the heap
480            VA      -   value of the element which replaces top element
481            VB      -   value of the tag
482
483          -- ALGLIB --
484             Copyright 28.02.2010 by Bochkanov Sergey
485        *************************************************************************/
486        public static void tagheapreplacetopi(ref double[] a,
487            ref int[] b,
488            int n,
489            double va,
490            int vb)
491        {
492            int j = 0;
493            int k1 = 0;
494            int k2 = 0;
495            double v = 0;
496            double v1 = 0;
497            double v2 = 0;
498
499            if( n<1 )
500            {
501                return;
502            }
503           
504            //
505            // N=1 is a special case
506            //
507            if( n==1 )
508            {
509                a[0] = va;
510                b[0] = vb;
511                return;
512            }
513           
514            //
515            // move down through heap:
516            // * J  -   current element
517            // * K1 -   first child (always exists)
518            // * K2 -   second child (may not exists)
519            //
520            // we don't write point to the heap
521            // until its final position is determined
522            // (it allow us to reduce number of array access operations)
523            //
524            j = 0;
525            k1 = 1;
526            k2 = 2;
527            while( k1<n )
528            {
529                if( k2>=n )
530                {
531                   
532                    //
533                    // only one child.
534                    //
535                    // swap and terminate (because this child
536                    // have no siblings due to heap structure)
537                    //
538                    v = a[k1];
539                    if( (double)(v)>(double)(va) )
540                    {
541                        a[j] = v;
542                        b[j] = b[k1];
543                        j = k1;
544                    }
545                    break;
546                }
547                else
548                {
549                   
550                    //
551                    // two childs
552                    //
553                    v1 = a[k1];
554                    v2 = a[k2];
555                    if( (double)(v1)>(double)(v2) )
556                    {
557                        if( (double)(va)<(double)(v1) )
558                        {
559                            a[j] = v1;
560                            b[j] = b[k1];
561                            j = k1;
562                        }
563                        else
564                        {
565                            break;
566                        }
567                    }
568                    else
569                    {
570                        if( (double)(va)<(double)(v2) )
571                        {
572                            a[j] = v2;
573                            b[j] = b[k2];
574                            j = k2;
575                        }
576                        else
577                        {
578                            break;
579                        }
580                    }
581                    k1 = 2*j+1;
582                    k2 = 2*j+2;
583                }
584            }
585            a[j] = va;
586            b[j] = vb;
587        }
588
589
590        /*************************************************************************
591        Heap operations: pops top element from the heap
592
593        PARAMETERS:
594            A       -   heap itself, must be at least array[0..N-1]
595            B       -   array of integer tags, which are updated according to
596                        permutations in the heap
597            N       -   size of the heap, N>=1
598
599        On output top element is moved to A[N-1], B[N-1], heap is reordered, N is
600        decreased by 1.
601
602          -- ALGLIB --
603             Copyright 28.02.2010 by Bochkanov Sergey
604        *************************************************************************/
605        public static void tagheappopi(ref double[] a,
606            ref int[] b,
607            ref int n)
608        {
609            double va = 0;
610            int vb = 0;
611
612            if( n<1 )
613            {
614                return;
615            }
616           
617            //
618            // N=1 is a special case
619            //
620            if( n==1 )
621            {
622                n = 0;
623                return;
624            }
625           
626            //
627            // swap top element and last element,
628            // then reorder heap
629            //
630            va = a[n-1];
631            vb = b[n-1];
632            a[n-1] = a[0];
633            b[n-1] = b[0];
634            n = n-1;
635            tagheapreplacetopi(ref a, ref b, n, va, vb);
636        }
637    }
638}
Note: See TracBrowser for help on using the repository browser.