so true

心怀未来,开创未来!
随笔 - 160, 文章 - 0, 评论 - 40, 引用 - 0
数据加载中……

calculate the maximum sum of sub-sequence in array

#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <sys/time.h>
#include <string>
#include <fstream>
#include <sstream>
#include <stdint.h>
#include <pthread.h>
#include <vector>
#include <map>
#include <set>

using namespace std;

void print_array(int* ary, int len) {
    for (int i = 0; i < len; ++i) {
        if (0 == i) {
            printf("%3d", ary[i]);
        } else {
            printf(" %3d", ary[i]);
        }
    }
    printf("\n");
}

int calc_max_sum2(int* ary, int len) {
    int max_ele = 1 << (8 * sizeof(int) - 1);
    int max_ele_pos = -1;
    int max = 0;

    int sum = 0;
    int start_pos = 0;
    int max_end_pos = -1;
    int max_start_pos = -1;
    for (int i = 0; i < len; ++i) {
        if (ary[i] > max_ele) {
            max_ele = ary[i];
            max_ele_pos = i;
        }
        sum += ary[i];
        if (sum < 0) {
            sum = 0;
            if (i + 1 < len) {
                start_pos = i + 1;
            }
        } else if (sum > max) {
            max = sum;
            max_end_pos = i;
            max_start_pos = start_pos;
        }
    }

    if (max_ele < 0) {
        max = max_ele;
        max_start_pos = max_ele_pos;
        max_end_pos = max_ele_pos;
    }

    printf("algorithm 2: max subsequence starts from %d, length:%d, max result:%d\n", max_start_pos, max_end_pos - max_start_pos + 1, max);
    print_array(ary + max_start_pos, max_end_pos - max_start_pos + 1);

    return max;
}

int calc_max_sum1(int* ary, int len) {
    if (NULL == ary || 0 == len) {
        return 0;
    }

    int max_ele = 1 << (8 * sizeof(int) - 1);
    int max_ele_pos = -1;

    int max_sum = 0;
    int max_start_pos = -1;
    int max_end_pos = -1;

    int cur_sum = 0; //reserve the optimal state
    int start_pos = -1; //record the start pos for cur_sum
    int end_pos = -1;//record the end pos for cur_sum
    int part_sum = 0; //track the incremental part, and merge into cur_sum once it is positive
    for (int i = 0; i < len; ++i) {
        if (ary[i] > max_ele) {
            max_ele = ary[i];
            max_ele_pos = i;
        }
        part_sum += ary[i];
        if (part_sum < 0) {
            if (cur_sum + part_sum < 0) {
                if (cur_sum > max_sum) {
                    max_sum = cur_sum;
                    max_start_pos = start_pos;
                    max_end_pos = end_pos;
                }

                cur_sum = 0;
                start_pos = -1;
                end_pos = -1;
                part_sum = 0;
            }
        } else if (part_sum > 0) {
            cur_sum += part_sum;
            part_sum = 0;
            end_pos = i;
            if (-1 == start_pos) {
                start_pos = i;
            }
        }
        //printf("%3d, cur_sum:%3d, start_pos:%3d, end_pos:%3d, part_sum:%3d, max_sum:%3d, max_start_pos:%3d, max_end_pos:%3d\n", i, cur_sum, start_pos, end_pos, part_sum, max_sum, max_start_pos, max_end_pos);
    }
    if (cur_sum > max_sum) {
        max_sum = cur_sum;
        max_start_pos = start_pos;
        max_end_pos = end_pos;
    }

    if (max_ele < 0) {
        max_sum = max_ele;
        max_start_pos = max_ele_pos;
        max_end_pos = max_ele_pos;
    }

    printf("algorithm 1: max subsequence starts from %d, length:%d, max result:%d\n", max_start_pos, max_end_pos - max_start_pos + 1, max_sum);
    print_array(ary + max_start_pos, max_end_pos - max_start_pos + 1);

    return max_sum;
}

int calc_sum(int* ary, int len) {
    int sum = 0;
    for (int i = 0; i < len; ++i) {
        sum += ary[i];
    }

    return sum;
}

int calc_max_sum_by_enumerate(int* ary, int len) {
    int max = 1 << (8 * sizeof(int) - 1);
    int begin = -1;
    int max_len = -1;
    for (int i = 0; i < len; ++i) {
        for (int j = i; j < len; ++j) {
            int sum = calc_sum(ary + i, j - i + 1);
            if (sum > max) {
                max = sum;
                begin = i;
                max_len = j - i + 1;
            }
        }
    }

    printf("algorithm of enumerate: max subsequence starts from %d, length:%d, max result:%d\n", begin, max_len, max);
    print_array(ary + begin, max_len);

    return max;
}

int main(int argc, char* argv[]) {
    int* ary = NULL;
    int len = 0;
    if (argc > 2) {
        len = argc - 1;
        ary = new int[len];
        for (int i = 1; i < argc; ++i) {
            ary[i - 1] = atoi(argv[i]);
        }
    } else if (2 == argc) {
        len = atoi(argv[1]);
        ary = new int[len];
        struct timeval tv;
        gettimeofday(&tv, NULL);
        srandom(tv.tv_usec);
        for (int i = 0; i < len; ++i) {
            ary[i] = (random() % 20) - 10;
        }
    } else {
        int tmp_ary[] = {-4, 6, -5, 3, -3, 4, -2};
        len = sizeof(tmp_ary) / sizeof(tmp_ary[0]);
        ary = new int[len];
        memcpy(ary, tmp_ary, sizeof(tmp_ary));
    }
    print_array(ary, len);
    int ret1 = calc_max_sum1(ary, len);
    int ret2 = calc_max_sum2(ary, len);
    int max = calc_max_sum_by_enumerate(ary, len);
    if (ret1 != max) {
        printf("algorithm 1 fails, result is %d, but the right answer is %d\n", ret1, max);
    } else if (ret2 != max) {
        printf("algorithm 2 fails, result is %d, but the right answer is %d\n", ret2, max);
    } else {
        printf("algorithm succeeds, max result:%d\n", max);
    }

    delete [] ary;
    return 0;
}

posted on 2015-03-10 10:52 so true 阅读(252) 评论(0)  编辑  收藏 所属分类: C&C++


只有注册用户登录后才能发表评论。


网站导航: