把一组数按(负,零,正)的顺序排序,时间复杂度O(n)

如题:把一组数按(负,零,正)的顺序排序,时间复杂度O(n),其中负数和正数部分不要求排序。

注:由于此处只判断正负数,所以输入的实例用 (-1,0,1 )表示即可。

基本思路:

1,用两个指针(left,preleft)记录左边位置,一个指针记录右边(right)位置。

2,首先从左向右运行,如果指针位置的值小于0 ,则继续向右。

3,当左边不小于 0 时,则从右向左运行,如果指针位置的值大于0, 则继续向左。

4,当左右指针位置的值都等于 0,则用 preleft 从左向右探索

      (1)当 preleft 指针位置的值小于等于 0 时,则继续探索

               a,小于 0,交换 arr[left] 和 arr[preleft],则 arr[left] < 0 , arr[preleft] = 0.

               b,等于 0,继续探索

5,左指针位置的值都大于 0,右指针位置的值都等于 0,交换他们。

6,左指针位置的值都等于 0,右指针位置的值都小于 0,交换他们。

7,左指针位置的值都大于 0,右指针位置的值都小于 0,交换他们。

 

#include "stdafx.h"
#include<iostream>
#include<string>

using namespace std;

void sortarray(int arr[],int length)
{
    int preleft = 0;
    int left = 0;
    int right = length-1;
    int temp;
    //set two point(preleft and left) to record the left position and 
    //one point(right) to record right position. both sides alternately run.
    while(preleft < right)
    {
        if(arr[preleft] < 0)   
        //if arr[i] at left position is negative, then continue to go right
        {
            ++preleft;
            ++left;
        }
        else if(arr[right] >0)
        //if arr[i] at right position is positive, then continue to go left.
        {
            --right;
        }
        else if((arr[preleft] == 0)&&(arr[right] == 0))
        //if both left and right are zero, then run the preleft point to have a try.
        {
            ++preleft;
            while((arr[preleft] <= 0)&&(preleft < right))
            //in this situation, we need go on.
            {
                if(arr[preleft] == 0)
                //if arr[preleft] equal to zero, continue to go right.
                {
                    ++preleft;
                }
                else if(arr[preleft] < 0)
                //if arr[preleft] is negative, exchange the value of arr[left] and arr[preleft].
                {
                    temp = arr[left];
                    arr[left] = arr[preleft];
                    arr[preleft] = temp;
                    ++left;
                }
            }
            if(arr[preleft] > 0)
            //if arr[preleft] is positive, then exchange the value of arr[preleft] and arr[right].
            {
                temp = arr[right];
                arr[right] = arr[preleft];
                arr[preleft] = temp;
                ++preleft;
            }
        }
        else if((arr[preleft] > 0) && (arr[right] == 0))
        //if left is positive and right is zero,then have a change. 
        {
            temp = arr[right];
            arr[right] = arr[preleft];
            arr[preleft] = temp;
            ++preleft;
            --right;
        }
        else if((arr[preleft] == 0) && (arr[right] < 0))
        // if left is zero and right is negative, then have a change.
        {
            temp = arr[right];
            arr[right] = arr[preleft];
            arr[preleft] = temp;
            ++preleft;
            ++left;            
        }
        else if((arr[preleft] > 0)&& (arr[right] < 0))
        //if left is positive and right is negative, then have a change.
        {
            temp = arr[right];
            arr[right] = arr[preleft];
            arr[preleft] = temp;
            ++left;
            ++preleft;
            --right;
        }
    }
}

void main()
{
    int arr[] = {1,-1,0,-1,0,-1,1,1,0,-1,1};
    int length = sizeof(arr)/sizeof(int);
    sortarray(arr,length);
    for(int i = 0; i < length; ++i)
    {
        cout<<arr[i]<<" ";
    }
    cout<<endl;
    system("pause");
}


 

输出:-1 -1 -1 -1 0 0 0 1 1 1 1

 

 

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值