top of page

CCC '16 S4 - Combining Riceballs

Updated: Aug 18, 2020


Solution 1:

recursive that is based on DP solution, please read DP notes:

#include <iostream>
#include <string.h>
using namespace std;
int n;
int sum[402];
int ans;
bool riceball_recur(int left, int right){
   if(left == right){
      ans = left > 0 ? max(ans, sum[right] - sum[left-1]):max(ans, sum[right]);
      return true;
   }
   if(right < left){
      return true;
   }
   int len = right - left + 1;
   for(int gap = 0; gap < len; gap++){

      for(int left_len = 0; left_len < len; left_len++){
         int leftend =left + left_len;
            int rightstart = leftend + gap + 1;
            if(rightstart > right){
               break;
            }
            else{
               int gapstart = leftend+1;
               int gapend = rightstart - 1;

               if(riceball_recur(left, leftend) &&
                  riceball_recur(gapstart, gapend) &&
                  riceball_recur(rightstart, right)){
                  int leftball =  left > 0?(sum[leftend] - sum[left-1]):sum[leftend];
                  int rightball = sum[right] - sum[rightstart-1];
                  if(leftball == rightball){
                     ans = left > 0 ? max(ans, sum[right] - sum[left-1]):max(ans, sum[right]);
                     return true;
                  }
               }
            }
      }
   }
   return false;
}
int main()
{
    cin >> n;
    for (int i = 0; i < n; i++)
    {
        int c;
        cin >> c;
        ans = max(ans, c);
        if (!i)
           sum[0]=c;
        else
           sum[i]=sum[i-1]+c;
    }
    riceball_recur(0, n-1);
    cout << ans;
    return 0;
}

Solution 2:

DP[i, j] is true if i to j can be merge, otherwise is false.

if i == j,

DP[i, j] = true and sum[i,j] and update max riceball.

else if j - i + 1 ==2 and raw[i] == raw[j]:

DP[i, j] = true and sum[i,j] and update max riceball .

else:

int left, right; i <= left< right<=j

if DP[i, left ] == true and DP[right, j] == true and DP[left+1, right-1] == true

and sum[i,left] == sum[right,j]

DP[i,j] = true and update max riceball


#include <iostream>
#include <string.h>
using namespace std;
int n;
int dp[402][402] = {0};
int sum[402];
int ans;

int main()
{
    cin >> n;
    for (int i = 0; i < n; i++)
    {
        cin >> dp[i][i];
        ans = max(ans, dp[i][i]);
        if (!i)
           sum[0]=dp[i][i];
        else
           sum[i]=sum[i-1]+dp[i][i];
    }
    for (int len = 1; len < n; len++)
    {
        for (int l = 0; l < n-len; l++)
        {
            int r = l+len;
            int j = l+1;
            int k = r;
            while(j<=k)
            {
                if (dp[l][j-1]&&
                    dp[l][j-1]==dp[k][r]&&
                    (j==k||dp[j][k-1]))
                {
                    dp[l][r]=max(dp[l][r],dp[l][j-1]+
                                 dp[j][k-1]+dp[k][r]);
                    ans=max(ans,dp[l][r]);
                    break;
                }
                if (sum[j-1]-sum[l-1]<sum[r]-sum[k-1])
                   j++;
                else
                   k--;
            }
        }
    }
    cout << ans;
    return 0;
}




Recent Posts

See All

CCC '24 J5 - Harvest Waterloo

#include<iostream> #include <vector> #include <algorithm> #include <cmath> #include <stack> using namespace std; int main() { int r, c,...

CCC '24 J4 - Troublesome Keys

s1 = input() s2 = input() silly = '' silly_o = '' quiete = '-' i = 0 j = 0 while i < len(s1) and j < len(s2): if s1[i] != s2[j]: if...

CCC '22 J5 - Square Pool

#include<iostream> #include <vector> #include <algorithm> #include <cmath> using namespace std; bool rowcom(pair<int, int> a, pair<int,...

Comentarios


bottom of page