Select sort explain - c++

I have problem understanding the selection sort algorithm where integers are rearranged from lowest to highest value. Here is the code:
#include<iostream>
using namespace std;
void SelectionSort(int A[], int n)
{
for (int i = 0; i < n-1; i++)
{
int iMin = i;
for (int j = i+1; j < n; j++)
{
if (A[j] < A[iMin])
iMin = j;
}
int temp = A[i];
A[i] = A[iMin];
A[iMin] = temp;
}
}
int main()
{
int A[] = {2, 4, 3, 5, 1};
SelectionSort(A, 5);
for (int i = 0; i < 5; i++)
cout<<A[i]<<" ";
}
Can someone help me by explaining in details how the integers are rearranged and give some comments to each line? Maybe its easy but I am dumb in programming. :(

In coding writing comments in each line doesn't usually make sense, because the line itself usually states very clearly what it does. What matters though is the structure.
What your algorithm does is go trough the list from beginning to end (the first for), and for each integer in the list, it swaps the current integer with the smallest integer in the rest of the list.
But to do this, it needs to find it first. This is where the second for comes in. It walks trough the rest of the list (because it starts at i and not at 0), and remembers the position (iMin) of the smallest integer.

Related

Array Sorting Issues in C++

I am trying to make a program that sorts an array without using the sort function (that won't work with objects or structs). I have made the greater than one work, but the less than one keeps changing the greatest element in the array to a one and sorting it wrong, and when used with the greater than function, the first element is turned into a large number. Can someone please help me fix this or is it my compiler.
void min_sort(int array[], const unsigned int size){
for(int k = 0; k < size; k++) {
for(int i = 0; i < size; i++) {
if(array[i] > array[i+1]){
int temp = array[i];
array[i] = array[i+1];
array[i+1] = temp;
}
}
}
}
You are not looping correctly. Looks like you are trying bubble sort which is:
void min_sort(int array[], const unsigned int size){
for(int k = 0; k < size; k++)
for(int i = k+1; i < size; i++)
if(array[i] < array[k]){
int temp = array[i];
array[i] = array[k];
array[k] = temp;
}
}
void min_sort(int array[], const unsigned int size)
{
for(int i=0;i<size-1;i++)
{
for(int j=0;j<size-1-i;j++)
{
if(array[j]>array[j+1])
{
swap(array[j] , array[j+1]);
}
}
}
}
I see that you are trying to implement the bubble sort algorithm. I have posted the code for bubble sort here. In bubble sort you basically compare the element at an index j and the element next to it at index j+1. If array[j] is greater than array[j+1] , you swap them using the swap() function or by using the temp method. The outer loop will run size - 1 times , and the inner loop will run size - 1 - i times because the last element will already be in place.
For Example we have an array of size 4 with elements such as :
array[i] = [100,90,8,10]
The bubble sort will sort it in the following steps :
90,100,8,10
90,8,100,10
90,8,10,100
8,90,10,100
8,10,90,100
8,10,90,100
See, the use of size-1-i . You can see the nested loop runs less number of times in each iteration of the outer loop.
There is only one mistake that your 2nd loop condition should be: i < size -1.
So it should be:
for (int i = 0; i < size -1; i++)
Your attempt at bubble sort is basically correct, you just have an out of bounds issue with your inner loop. During the inner loop's last run, i == size - 1, therefore i + 1 is equal to size, thus data[i+1] is out of range. Simply change the condition of your for to be i < size - 1.
Working example: https://godbolt.org/z/e5ohWPfTz

Solution for maximum xor secondary in an array of integers

I am trying to solve this codeforces problem
http://codeforces.com/contest/281/problem/D
Given an array of integers, find the maximum xor of the first and second max element in any of the sub sequences ?
I am not able to figure out the optimal approach to solve this problem. Few of the solving techniques I articulated was using sorting, stack but I could not figure out the right solution.
I googled and found out the problem setter's code for the solution. But I could not understand the solution as it is in c++ and I am naive to it.
Below is the problem setter's code in c++
using namespace std;
using namespace io;
typedef set<int> Set;
typedef set<int, greater<int> > SetRev;
namespace solution {
const int SIZE = 100000 + 11;
int n;
int A[SIZE];
II S[SIZE];
Set P;
SetRev P_rev;
int result;
}
namespace solution {
class Solver {
public:
void solve() {
normalize();
result = get_maximum_xor();
}
int get_maximum_xor() {
int res = 0;
for (int i = 0; i < n; i++) {
int current_value = S[i].first;
Set::iterator it_after = P.upper_bound(S[i].second);
Set::iterator it_before = P_rev.upper_bound(S[i].second);
if (it_after != P.end()) {
int after_value = A[*it_after];
res = max(res, current_value ^ after_value);
}
if (it_before != P_rev.end()) {
int before_value = A[*it_before];
res = max(res, current_value, before_value);
}
P.insert(S[i].second);
P_rev.insert(S[i].second);
}
return res;
}
void normalise() {
for (int i = 0; i < n; i++) {
S[i] = II(A[i], i);
}
sort(S, S + n, greater<II>());
}
}
Can someone please explain me the solution, the approach used as I understand it in pieces and not totally ?
Ok, so Solver::solve() starts by calling normalise:
void normalise() {
for (int i = 0; i < n; i++) {
S[i] = II(A[i], i);
}
sort(S, S + n, greater<II>());
}
What that's doing is taking an array A of integers - say {4, 2, 9}, and populating an array S where A's values are sorted and paired with the index at which they appear in A - for our example, {{2, 1}, {4, 0}, {9, 2}}.
Then the solver calls get_maximum_xor()...
for (int i = 0; i < n; i++) {
int current_value = S[i].first;
Set::iterator it_after = P.upper_bound(S[i].second);
Set::iterator it_before = P_rev.upper_bound(S[i].second);
The "for i" loop is used to get successive sorted values from S (those values originally from A). While you haven't posted a complete program, so we can't know for sure nothing's prepopulating any values in P, I'll assume that. We do know P's is a std::map and upper_bound searches to find the first element in P greater than S[i].second (the index at which current_value appeared in A) and values above, then something similar for P_rev which is a std::map in which values are sorted in descending order, likely it will be kept populated with the same values as P but again we don't have the code.
Then...
if (it_after != P.end()) {
int after_value = A[*it_after];
res = max(res, current_value ^ after_value);
}
...is saying that if any of the values in P were >= S[i].second, look up A at the index it_after found (getting a sense now that P tracks the last elements in each subsequence (?)), and if the current_value XORed with that value from A is more than any earlier result candidate (res), then update res with the new larger value.
It does something similar with P_rev.
Finally...
P.insert(S[i].second);
P_rev.insert(S[i].second);
Adds the index of current_value in A to P and P_rev for future iterations.
So, while I haven't explained why or how the algorithm works (I haven't even read the problem statement), I think that should make it clear what the C++ is doing which is what you said you're struggling with - you're on your own for the rest ;-).

C++ Part of brute-force knapsack

reader,
Well, I think I just got brainfucked a bit.
I'm implementing knapsack, and I thought about I implemented brute-force algorithm like 1 or 2 times ever. So I decided to make another one.
And here's what I chocked in.
Let us decide W is maximum weight, and w(min) is minimal-weighted element we can put in knapsack like k=W/w(min) times. I'm explaining this because you, reader, are better know why I need to ask my question.
Now. If we imagine that we have like 3 types of things we can put in knapsack, and our knapsack can store like 15 units of mass, let's count each unit weight as its number respectively. so we can put like 15 things of 1st type, or 7 things of 2nd type and 1 thing of 1st type. but, combinations like 22222221[7ed] and 12222222[7ed] will mean the same for us. and counting them is a waste of any type of resources we pay for decision. (it's a joke, 'cause bf is a waste if we have a cheaper algorithm, but I'm very interested)
As I guess the type of selections we need to go through all possible combinations is called "Combinations with repetitions". The number of C'(n,k) counts as (n+k-1)!/(n-1)!k!.
(while I typing my message I just spotted a hole in my theory. we will probably need to add an empty, zero-weighted-zero-priced item to hold free space it's probably just increases n by 1)
so, what's the matter.
https://rosettacode.org/wiki/Combinations_with_repetitions
as this problem is well-described up here^ I don't really want to use stack this way, I want to generate variations in single cycle, which is going from i=0 to i<C'(n,k).
so, If I can make it, how it works?
we have
int prices[n]; //appear mystically
int weights[n]; // same as previous and I guess we place (0,0) in both of them.
int W, k; // W initialized by our lord and savior
k = W/min(weights);
int road[k], finalroad[k]; //all 0
int curP = curW = maxP = maxW = 0;
for (int i = 0; i < rCombNumber(n, k); i ++) {
/*guys please help me to know how to generate this mask which is consists of indices from 0 to n (meaning of each element) and k is size of mask.*/
curW = 0;
for (int j = 0; j < k; j ++)
curW += weights[road[j]];
if (curW < W) {
curP = 0;
for (int l = 0; l < k; l ++)
curP += prices[road[l]];
if (curP > maxP) {
maxP = curP;
maxW = curW;
finalroad = road;
}
}
}
mask, road -- is an array of indices, each can be equal from 0 to n; and have to be generated as C'(n,k) (link about it above) from { 0, 1, 2, ... , n } by k elements in each selection (combination with repetitions where order is unimportant)
that's it. prove me wrong or help me. Much thanks in advance _
and yes, of course algorithm will take the hell much time, but it looks like it should work. and I'm very interesting in it.
UPDATE:
what do I miss?
http://pastexen.com/code.php?file=EMcn3F9ceC.txt
The answer was provided by Minoru here https://gist.github.com/Minoru/745a7c19c7fa77702332cf4bd3f80f9e ,
it's enough to increment only the first element, then we count all of the carries, set where we did a carry and count reset value as the maximum of elements to reset and reset with it.
here's my code:
#include <iostream>
using namespace std;
static long FactNaive(int n)
{
long r = 1;
for (int i = 2; i <= n; ++i)
r *= i;
return r;
}
static long long CrNK (long n, long k)
{
long long u, l;
u = FactNaive(n+k-1);
l = FactNaive(k)*FactNaive(n-1);
return u/l;
}
int main()
{
int numberOFchoices=7,kountOfElementsInCombination=4;
int arrayOfSingleCombination[kountOfElementsInCombination] = {0,0,0,0};
int leftmostResetPos = kountOfElementsInCombination;
int resetValue=1;
for (long long iterationCounter = 0; iterationCounter<CrNK(numberOFchoices,kountOfElementsInCombination); iterationCounter++)
{
leftmostResetPos = kountOfElementsInCombination;
if (iterationCounter!=0)
{
arrayOfSingleCombination[kountOfElementsInCombination-1]++;
for (int anotherIterationCounter=kountOfElementsInCombination-1; anotherIterationCounter>0; anotherIterationCounter--)
{
if(arrayOfSingleCombination[anotherIterationCounter]==numberOFchoices)
{
leftmostResetPos = anotherIterationCounter;
arrayOfSingleCombination[anotherIterationCounter-1]++;
}
}
}
if (leftmostResetPos != kountOfElementsInCombination)
{
resetValue = 1;
for (int j = 0; j < leftmostResetPos; j++)
{
if (arrayOfSingleCombination[j] > resetValue)
{
resetValue = arrayOfSingleCombination[j];
}
}
for (int j = leftmostResetPos; j != kountOfElementsInCombination; j++)
{
arrayOfSingleCombination[j] = resetValue;
}
}
for (int j = 0; j<kountOfElementsInCombination; j++)
{
cout<<arrayOfSingleCombination[j]<<" ";
}
cout<<"\n";
}
return 0;
}
thanks a lot, Minoru

Bubble Sort Using Slides instead of swaps

currently I'm being asked to design four sorting algorithms (insertion, shell, selection, and bubble) and I have 3 of the 4 working perfectly; the only one that isn't functioning correctly is the Bubble Sort. Now, I'm well aware of how the normal bubble sort works with using a temp var to swap the two indexes, but the tricky part about this is that it needs to use the array index[0] as a temp instead of a normal temp, which is used in swapping, and slide the lower array variables down to the front of the list and at the end of the pass assign the last index to the temp which is the greatest value.
I've been playing around with this for a while and even tried to look up references but sadly I cannot find anything. I'm hoping that someone else has done this prior and can offer some helpful tips. This is sort of a last resort as I've been modifying and running through the passes with pen and paper to try and find my fatal error. Anyways, my code is as follows...
void BubbleSort(int TheArray[], int size)
{
for (int i = 1; i < size + 1; i++)
{
TheArray[0] = TheArray[i];
for (int j = i + 1; j < size; j++)
{
if (TheArray[j] > TheArray[0])
TheArray[0] = TheArray[j];
else
{
TheArray[j - 1] = TheArray[j];
}
}
TheArray[size- 1] = TheArray[0];
}
}
Thanks for any feedback whatsoever; it's much appreciated.
If I understand the problem statement, I think you're looking for something along these lines :
void BubbleSort(int theArray[], int size)
{
for (int i = 1; i < size + 1; i++)
{
theArray[0] = theArray[1];
for (int j = 1; j <= size + 1 - i; j++)
{
if (theArray[j] > theArray[0])
{
theArray[j-1] = theArray[0];
theArray[0] = theArray[j];
}
else
{
theArray[j - 1] = theArray[j];
}
}
theArray[size-i+1] = theArray[0];
}
}
The piece that you're code was missing, I think, was that once you find a new maximum, you have to put it back in the array before placing the new maximum in theArray[0] storage location (see theArray[j-1] = theArray[0] after the compare). Additionally, the inner loop wants to run one less each time since the last element will be the current max value so you don't want to revisit those array elements. (See for(int j = 1 ; j <= size + 1 - i ; j++))
For completeness, here's the main driver I used to (lightly) test this :
int main()
{
int theArray[] = { 0, 5, 7, 3, 2, 8, 4, 6 };
int size = 7;
BubbleSort(theArray, size);
for (int i = 1; i < size + 1; i++)
cout << theArray[i] << endl;
return 0;
}

Insert values from one array to another directly sorted

So what I have to do is insert certain values from one array to another one directly sorted without having to sort them later using BubbleSort or QuickSort or any other method. I can't think of a way to do this... I have to insert them from the biggest value to the smallest one. Here's what I have until now:
void palindroame (int x[100], int y[100]) {
int i=0, j, k=0, aux;
while (x[i]!=0) {
k++; i++;
}
i=0;
for (i=0; i<=k-1; i++) y[i]=0;
for (i=0; i<=k-1; i++) {
if (palindrom(x[i])!=0 && palindrom(x[i+1])!=0)
if (x[i]<x[i+1]) {
aux=x[i+1]; x[i+1]=x[i]; x[i]=aux;
}
} //wrong
for (i=0; i<=k-1; i++) {
if (palindrom(x[i])) y[i]=x[i];
} //wrong
}
Thanks in advance!
The algorithm you need is selection sort, you can use this to sort and copy at the same time.
You can have a look at priority queues:
http://www.cplusplus.com/reference/queue/priority_queue/
Heres an example of a selection sort i have done recently (in which a is a vector)
should give you enough to go on hope it helps, ask questions if u like
for (unsigned int i = 0; i < a.size()-1; i++)
{
int min = i;
for(unsigned int j = i +1; j < a.size(); j++)
{
// If new minimum is found then stores this as the new minimum
if(a[j] < a[min])
{
min = j;
}
}
// Stores the values in the array in ascending order
if (min != i)
{
int temp = a[i];
a[i] = a[min];
a[min] = temp;
}
}
// Returns the array in ascending order
return a;
Edit: just to clarify this is working on a vector that already has values in it in case that wasnt clear but example with code comments i think is enough to help you IMO