Joseph's arrangement

Source: Internet
Author: User

Thinking and analysis:

If M is a constant, you can use a circular linked list and head or tail pointer to indicate the loop structure easily. After cyclic output, the node is deleted n times. During each outer loop, the inner layer is fixed for m times. Therefore, the running time is O (Mn) = O (n ).

M is not a constant. The size attribute can be used to record the location of each node in the current tree. After a remainder process, each node can be correctly found and output to delete each node. After N cycles, each cycle needs to find a node output and delete it, therefore, it takes O (lgn) Time for each loop. The total running time is O (nlgn ).

The Code is as follows:

When M is a constant:

#include <iostream>using namespace std;#define n 10#define m 3#define LEN sizeof(struct circular_list)struct circular_list{   int key;   struct circular_list* next;};struct circular_list*tail=NULL;struct circular_list*Insert(struct circular_list*&head,int k){struct circular_list*z=new struct circular_list[LEN];z->key=k;    if (head==NULL)    {head=tail=z;head->next=tail;    }else{tail->next=z;z->next=head;tail=z;}return head;}struct circular_list* Delete(struct circular_list*&head,struct circular_list*z){   struct circular_list*p=head;   while (p->next!=z)   {   p=p->next;   }   if (head==tail)   {   p->next=NULL;   }   else    {   if (head==p->next)   {     head=p->next->next;   }   else if (tail==p->next)   { tail=p;   }   p->next=p->next->next;   }   return p->next;}void n_m_Josephus(struct circular_list*&head){   struct circular_list*p=head;   while (p)   {   int i=0;   while (i!=m-1)   {   p=p->next;   i++;   }   struct circular_list*z=p;   cout<<z->key<<" ";       p=Delete(head,z);   }}void main(){    int a[n]={0};for (int i=0;i<n;i++){a[i]=i+1;}int j=0;struct circular_list*head=NULL;    while (j!=n)    {head=Insert(head,a[j]);j++;;    }    struct circular_list*p=head;do {cout<<p->key;p=p->next;} while (p!=head);cout<<endl;n_m_Josephus(head);}

When M is not a constant:

# Include <iostream> # include <time. h> using namespace STD; # define black 0 # define Red 1 # define nil-1 # define Len sizeof (struct OS _tree) struct OS _tree {struct OS _tree * right, * left; struct OS _tree * parent; int key, color, size; // size indicates the number of knots in the subtree .}; Struct OS _tree * root = NULL, * nil = NULL; void left_rotate (struct OS _tree * X) {// left rotation: Describes the rotation code in three steps ① ③. Struct OS _tree * Y = x-> right; // set the y node. X-> right = Y-> left; // the code in this line and the IF structure below indicate that "the left child of Y becomes the right child of X ". ① If (Y-> left! = Nil) {Y-> left-> parent = x;} y-> parent = x-> parent; // The line of code and the following if-else structure expression process is "Y becomes the new root of the subtree ". ② If (X-> parent = nil) {root = y;} else if (x = x-> parent-> left) {X-> parent-> left = y;} else X-> parent-> right = y; y-> left = X; // This line of code and the following line both express "X is the left child of Y ". ③ X-> parent = y; y-> size = x-> size; // maintenance of additional information X-> size = x-> left-> size + X-> right-> size + 1;} void right_rotate (struct OS _tree * X) {// right rotation: Describes the rotation code in three steps (①) (③. Struct OS _tree * Y = x-> left; // set the y node. X-> left = Y-> right; // This line of code and the IF structure below indicate that "the left child of Y becomes the right child of X ". ① If (Y-> right! = Nil) {Y-> right-> parent = x;} y-> parent = x-> parent; // The line of code and the following if-else structure expression process is "Y becomes the new root of the subtree ". ② If (X-> parent = nil) {root = y;} else if (x = x-> parent-> right) {X-> parent-> right = y;} else X-> parent-> left = y; y-> right = X; // This line of code and the following line both express "X is the left child of Y ". ③ X-> parent = y; y-> size = x-> size; // maintenance of additional information X-> size = x-> left-> size + X-> right-> size + 1;} void rb_insert_fixup (struct OS _tree * z) {While (Z-> parent-> color = red) {If (Z-> parent = z-> parent-> left) {struct OS _tree * Y = z-> parent-> right; // If (Y-> color = red) // scenario 1: the primary node is red {// color P1, y, and P2 to keep the property 5. And solved the problem that the parent node of Z and Z are both red nodes Z-> parent-> color = black; y-> color = black; z-> parent-> color = Red; Z = z-> parent; // take z's grandfather node as the new node Z into the next loop} else {If (Z = z-> parent-> right) // Scenario 2: check whether Z is a right child and the primary node is black, provided that the P1 node is not a leaf node {// use a left-hand node to convert case 2 to case 3 Z = z-> parent; left_rotate (z); // after entering the if statement, we can see that the rotating node cannot be a leaf node, so we don't have to judge whether Z is a leaf node.} Z-> parent-> color = black; // Case 3: Z is a left child and the uncle node is black, change the color of the parent and grandfather node of Z and perform a right-hand operation to keep the properties 5 Z-> parent-> color = Red; right_rotate (Z-> parent); // Since P2 may be a leaf node, it is best to use an if to judge} else // The else branch below is similar to the above, note that the rotation in Case 2 and Case 3 of the else branch is exactly the inverse of the IF branch. {Struct OS _tree * Y = z-> parent-> left; If (Y-> color = red) {z-> parent-> color = black; y-> color = black; Z-> parent-> color = Red; Z = z-> parent ;} else {If (Z = z-> parent-> left) {z = z-> parent; right_rotate (z);} Z-> parent-> color = black; z-> parent-> color = Red; left_rotate (Z-> parent) ;}} root-> color = black; // Finally, the root point is black .} Void rb_insert (struct OS _tree * z) {struct OS _tree * Y = nil; struct OS _tree * x = root; while (X! = Nil) {X-> size ++; y = x; If (Z-> key <X-> key) {x = x-> left ;} else x = x-> right;} Z-> parent = y; If (y = nil) {root = z ;} else if (Z-> key <Y-> key) {Y-> left = z;} else y-> right = z; Z-> left = nil; // assign a blank value to the left and right children of the inserted node. Z-> right = nil; Z-> color = Red; // The insert node is red. Z-> size = 1; Z-> left-> size = 0; Z-> right-> size = 0; rb_insert_fixup (z );} void rb_transplant (struct OS _tree * u, struct OS _tree * V) {If (u-> parent = nil) root = V; else if (u = u-> parent-> left) U-> parent-> left = V; else u-> parent-> right = V; v-> parent = u-> parent;} struct OS _tree * tree_minimum (struct OS _tree * X) // calculates the minimum value of the current node of the Binary Search Tree {While (X! = Nil & X-> left! = Nil) {x = x-> left;} return X;} struct OS _tree * tree_maxinum (struct OS _tree * X) // calculates the maximum value of the current node of the Binary Search Tree {While (X! = Nil & X-> right! = Nil) {x = x-> right;} return X;} struct OS _tree * tree_predecessor (struct OS _tree * X) // search for the front of the Binary Search Tree {If (X-> left! = Nil) {return tree_maxinum (X-> left);} struct OS _tree * Y = x-> parent; while (y! = Nil & X = Y-> left) {x = y; y = Y-> parent;} return y;} struct OS _tree * tree_successor (struct OS _tree * X) // find the successor of the Binary Search Tree {If (X-> right! = Nil) {return tree_minimum (X-> right);} struct OS _tree * Y = x-> parent; while (y! = Nil & X = Y-> right) {x = y; y = Y-> parent;} return y ;} // non-recursive Binary Search Tree lookup function struct OS _tree * iterative_tree_search (struct OS _tree * X, int K) {While (X! = Nil & K! = X-> key) {If (k <X-> key) {x = x-> left;} else x = x-> right;} return X ;} void rb_delete_fixup (struct OS _tree * X) {struct OS _tree * w = NULL; // W is the sibling node of X while (X! = Root & X-> color = black) // If X is black and is not the root node, the loop is executed. {// X is a node with dual colors. The purpose of adjustment is to move the black attribute of X up. If (x = x-> parent-> left) {W = x-> parent-> right; if (W-> color = red) // scenario 1: x's sibling node W is red. {// Change the color of W and X. P + one rotation to Case 2, 3, and 4. W-> color = black; X-> parent-> color = Red; left_rotate (X-> parent); W = x-> parent-> right ;} if (W-> left-> color = Black & W-> right-> color = black) // Case 2: X's sibling node W is black, in addition, both child nodes of W are black. {W-> color = Red; // remove a heavy black from X and W. X is black, and W is red. X = x-> parent; // The x node moves up to become the new node to be adjusted.} Else {If (W-> right-> color = black) // Case 3: The sibling node W of X is black, and the left child of W is red, w's right child is black. {// Switch the color + rotation of W and W. Left to case 4. W-> left-> color = black; W-> color = Red; right_rotate (w); W = x-> parent-> right ;} w-> color = x-> parent-> color; // The following is the case 4: The sibling node W of X is black, and the right child of W is red. X-> parent-> color = black; // set X. P and W. Right to black + rotate to remove the extra black of X. W-> right-> color = black; left_rotate (X-> parent); X = root; // X becomes the root node and ends the loop.} The following else // is similar to the IF branch above. {W = x-> parent-> left; If (W-> color = red) {w-> color = black; X-> parent-> color = Red; right_rotate (X-> parent); W = x-> parent-> left ;} if (W-> left-> color = Black & W-> right-> color = black) {w-> color = Red; X = x-> parent;} else {If (W-> left-> color = black) {w-> right-> color = black; w-> color = Red; left_rotate (w); W = x-> parent-> left;} w-> color = x-> parent-> color; x-> parent-> color = black; W-> left-> color = black; right_rot Ate (X-> parent); X = root; }}x-> color = black;} void rb_delete (struct OS _tree * z) {struct OS _tree * Y = Z, * X; // y indicates the node to be deleted or moved. Int y_original_color = Y-> color; // saves the original color of Y to prepare for the final adjustment. Struct OS _tree * t = z-> parent; If (Z-> left = nil) {While (T! = Nil) {T-> size --; t = T-> parent;} X = z-> right; // X points to the unique subnode or leaf node of Y, save the trace of x and move it to the original position of Y. rb_transplant (z, Z-> right); // set the path to Z. replace the subtree with Z as the root of right .} Else if (Z-> right = nil) {While (T! = Nil) {T-> size --; t = T-> parent;} X = z-> left; // X points to the unique subnode or leaf node of Y, save the trace of x and move it to the original position of Y. replace left with the child tree with Z as the root .} Else {Y = tree_minimum (Z-> right); // find the successor of Z. Right. Struct OS _tree * t = Y-> parent; y-> size = z-> size-1; // y replaces the original position of Z, therefore, the size attribute is-1 while (T! = Nil) {T-> size --; t = T-> parent;} The new original node of y_original_color = Y-> color; // y is reset. X = Y-> right; // X points to the unique subnode or leaf node of Y, save the trace of x and move it to the original position of Y. If (Y-> parent = z) {X-> parent = y; // because the parent node of Z is the node to be deleted, it cannot be directed to it, so it points to y} else {rb_transplant (Y, Y-> right); // set Y. replace the subtree with Y as the root of right. Y-> right = z-> right; y-> right-> parent = y;} rb_transplant (z, y ); // Replace the subtree rooted in Y with the subtree rooted in Z. Y-> left = z-> left; y-> left-> parent = y; y-> color = z-> color; // assign the color of the deleted node to Y to ensure that the color of the tree structure above y remains the same .} If (y_original_color = black) // The original color of Y is black, indicating that you need to adjust the red and black colors. Rb_delete_fixup (x);} // traverse void inodertraverse (struct OS _tree * P) {If (P! = Nil) {inodertraverse (p-> left); cout <p-> key <"<p-> color <" <"rank: "<p-> size <Endl; inodertraverse (p-> right) ;}} struct OS _tree * OS _select (struct OS _tree * & X, int I) // find the element of the given rank in the sequence statistics tree {int r = x-> left-> size + 1; if (I = r) {return X ;} else if (I <r) {return OS _select (X-> left, I);} else return OS _select (X-> right, I-r );} int iterative_ OS _rank (struct OS _tree * & T, struct OS _tree * X) // determine the rank of the sequence statistics tree {int r = x-> left-> size + 1; Struct OS _tree * Y = x; while (y! = Root) {If (y = Y-> parent-> right) {r = R + Y-> parent-> left-> size + 1 ;} y = Y-> parent;} return r;} void n_m_joseph PHUs (struct OS _tree * X, int M, int N) {x = root; Int J = 0, I = n, T = 1; while (root! = Nil) {J = (t + m-1) % I; If (j = 0) J = I; struct OS _tree * Y1 = OS _select (root, J ); // Y1 indicates the cout <Y1-> key <""; // output node rb_delete (Y1); // Delete T = J after the output node; I -- ;}} void main () {srand (unsigned) Time (null); int m = 0, n = 0; cout <"Enter the M and N values in the n_m_joseph us Arrangement" <Endl; cout <"m ="; CIN> m; cout <"n ="; CIN> N; int * array1 = new int [N]; for (Int J = 0; j <n; j ++) {array1 [J] = J + 1; cout <array1 [J] <"" ;}cout <Endl; nil = new struct OS _tree [Len]; nil-> Key = nil; nil-> color = black; root = nil; int I = 0; struct OS _tree * root = new struct OS _tree [Len]; root-> key = array1 [I ++]; rb_insert (Root); root = root; while (I! = N) {struct OS _tree * z = new struct OS _tree [Len]; Z-> key = array1 [I]; rb_insert (z); I ++ ;} inodertraverse (Root); cout <"Joseph arrangement:"; n_m_joseph PHUs (root, m, n );}
SummaryPart A of Joseph's arrangement uses chapter 1, while Part B uses the knowledge of this chapter. This is a simple application of learned knowledge. I think this program is quite interesting.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.