题目:输入一个整数数组,实现一个函数来调整该数组中数字的顺序,使得所有奇数位于数组的前半部分,所有偶数位于数组的后半部分。
1、一般想法,不考虑时间复杂度:
每次遍历数组,碰到一个偶数就拿出来,将后面所有数字向前挪动一位,在将该偶数放到最后。
2、利用冒泡排序的思想,两个指针,一前以后,如果前为偶数,后为奇数,就交换。
算法如下:
void Reorder_array(int p[],int length) { if(NULL == p || length <= 0) return; int i,j; int temp; for(i = 0; i < length; i++) { for(j = length - 1; j > i; j--) { if(p[i]%2 == 0 && p[j]%2 != 0) /**头指向偶数,尾指向奇数,交换两者*/ { temp = p[i]; p[i] = p[j]; p[j] = temp; } if(p[i]%2 != 0) /**头指针指向奇数,跳出内循环,i++*/ { break; } /**尾指针指向偶数,就什么不干,等待j--*/ } } for(i = 0; i < length; i++){ cout << p[i] << ' '; } cout << endl; }下面是书上的写法,感觉比我写的好:
逻辑比较清晰,并且用 位与运算,代替了 取余运算,提高了运算效率。
void Reorder_array_from_book(int *pData, unsigned int length) { if(pData == NULL || length == 0) return; int *pBegin = pData; int *pEnd = pData + length - 1; while(pBegin < pEnd) { while(pBegin < pEnd && (*pBegin & 0x1) != 0) /**取余运算用 & 代替了*/ pBegin++; while(pBegin < pEnd && (*pEnd & 0x1) == 0) pEnd--; if(pBegin < pEnd) { int temp = *pBegin; *pBegin = *pEnd; *pEnd = temp; } } }考虑 位与 运算,并且考虑 算法的扩展性,使用了函数指针。
/**函数指针写法,可提高扩展性,需要重视*/ bool isEven(int pData) { return (pData & 0x1) == 0; } void Reorder_array_pre(int p[],int length,bool (*func)(int)) { if(NULL == p || length <= 0) return; int i,j; int temp; for(i = 0; i < length; i++) { for(j = length - 1; j > i; j--) { if(func(p[i]%2) && !func(p[j]%2)) /**头指向偶数,尾指向奇数,交换两者*/ { temp = p[i]; p[i] = p[j]; p[j] = temp; } if(!func(p[j]%2)) /**头指针指向奇数,跳出内循环,i++*/ { break; } /**尾指针指向偶数,就什么不干,等待j--*/ } } for(i = 0; i < length; i++){ cout << p[i] << ' '; } cout << endl; }测试代码:
int main() { //int p[11] = {1,2,3,4,5,9,3,11,66,55,68}; int p[10] = {0,1,2,3,4,5,6,7,8,9}; //int p[8] = {2,2,2,2,1,1,1,1}; //int p[1] = {1}; //Reorder_array(p,8); Reorder_array_pre(p,10,isEven); /**这里传递的是指针,所以是改变了原数组的内容*/ /* for(int i = 0; i < 10; i++){ cout << p[i] << ' '; } cout << endl; */ return 0; }
结果:
/*点滴积累,我的一小步O(∩_∩)O~*/
版权声明:本文为博主原创文章,未经博主允许不得转载。
剑指offer_面试题14_调整数组顺序使奇数位于偶数前面(函数指针用法)
原文地址:http://blog.csdn.net/jwentao01/article/details/47379825