      void merge(_cimg_math_parser& mp) {
        if (&mp==this) return;
        cimg_rofY(mp.memmerge,k) {
          const unsigned int
            pos = (unsigned int)mp.memmerge(0,k),
            siz = (unsigned int)mp.memmerge(1,k),
            iop = (unsigned int)mp.memmerge(2,k);
          if (!siz) switch (iop) { // Scalar value
            case 0 : mp.mem[pos] = mem[pos]; break;                                       // Assignment
            case 1 : mp.mem[pos]+=mem[pos]; break;                                        // Operator+
            case 2 : mp.mem[pos]-=mem[pos]; break;                                        // Operator-
            case 3 : mp.mem[pos]*=mem[pos]; break;                                        // Operator*
            case 4 : mp.mem[pos]/=mem[pos]; break;                                        // Operator/
            case 5 : mp.mem[pos] = (double)((longT)mp.mem[pos] & (longT)mem[pos]); break; // Operator&
            case 6 : mp.mem[pos] = (double)((longT)mp.mem[pos] | (longT)mem[pos]); break; // Operator|
            case 7 : mp.mem[pos] = (double)((longT)mp.mem[pos] ^ (longT)mem[pos]); break; // Operator 'xor'
            case 8 : mp.mem[pos] = mp.mem[pos] && mem[pos]; break;                        // Operator&&
            case 9 : mp.mem[pos] = mp.mem[pos] || mem[pos]; break;                        // Operator||
            case 10 : mp.mem[pos] = std::min(mp.mem[pos],mem[pos]); break;                // Operator 'min'
            case 11 : mp.mem[pos] = std::max(mp.mem[pos],mem[pos]); break;                // Operator 'max'
            } else switch (iop) { // Vector value
            case 0 : // Assignment
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true) = CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 1 : // Operator+
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)+=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 2 : // Operator-
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)-=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 3 : // Operator*
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)*=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 4 : // Operator/
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)/=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 5 : // Operator&
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)&=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 6 : // Operator|
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)|=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 7 : // Operator 'xor'
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)^=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 8 : { // Operator&&
              CImg<doubleT>
                arg1(&mp.mem[pos + 1],siz,1,1,1,true),
                arg2(&mem[pos + 1],siz,1,1,1,true);
              cimg_foroff(arg1,off) arg1[off] = arg1[off] && arg2[off];
              } break;
            case 9 : { // Operator||
              CImg<doubleT>
                arg1(&mp.mem[pos + 1],siz,1,1,1,true),
                arg2(&mem[pos + 1],siz,1,1,1,true);
              cimg_foroff(arg1,off) arg1[off] = arg1[off] || arg2[off];
            } break;
            case 10 : // Operator 'min'
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true).min(CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true));
              break;
            case 11 : // Operator 'max'
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true).max(CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true));
              break;
            }
        }
      }
      void merge(_cimg_math_parser& mp) {
        if (&mp==this) return;
        cimg_rofY(mp.memmerge,k) {
          const unsigned int
            pos = (unsigned int)mp.memmerge(0,k),
            siz = (unsigned int)mp.memmerge(1,k),
            iop = (unsigned int)mp.memmerge(2,k);
          if (!siz) switch (iop) {  
            case 0 : mp.mem[pos] = mem[pos]; break;                                        
            case 1 : mp.mem[pos]+=mem[pos]; break;                                         
            case 2 : mp.mem[pos]-=mem[pos]; break;                                         
            case 3 : mp.mem[pos]*=mem[pos]; break;                                         
            case 4 : mp.mem[pos]/=mem[pos]; break;                                         
            case 5 : mp.mem[pos] = (double)((longT)mp.mem[pos] & (longT)mem[pos]); break;  
            case 6 : mp.mem[pos] = (double)((longT)mp.mem[pos] | (longT)mem[pos]); break;  
            case 7 : mp.mem[pos] = (double)((longT)mp.mem[pos] ^ (longT)mem[pos]); break;  
            case 8 : mp.mem[pos] = mp.mem[pos] && mem[pos]; break;                         
            case 9 : mp.mem[pos] = mp.mem[pos] || mem[pos]; break;                         
            case 10 : mp.mem[pos] = std::min(mp.mem[pos],mem[pos]); break;                 
            case 11 : mp.mem[pos] = std::max(mp.mem[pos],mem[pos]); break;                 
            } else switch (iop) {  
            case 0 :  
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true) = CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 1 :  
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)+=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 2 :  
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)-=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 3 :  
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)*=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 4 :  
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)/=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 5 :  
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)&=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 6 :  
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)|=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 7 :  
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true)^=CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true);
              break;
            case 8 : {  
              CImg<doubleT>
                arg1(&mp.mem[pos + 1],siz,1,1,1,true),
                arg2(&mem[pos + 1],siz,1,1,1,true);
              cimg_foroff(arg1,off) arg1[off] = arg1[off] && arg2[off];
              } break;
            case 9 : {  
              CImg<doubleT>
                arg1(&mp.mem[pos + 1],siz,1,1,1,true),
                arg2(&mem[pos + 1],siz,1,1,1,true);
              cimg_foroff(arg1,off) arg1[off] = arg1[off] || arg2[off];
            } break;
            case 10 :  
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true).min(CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true));
              break;
            case 11 :  
              CImg<doubleT>(&mp.mem[pos + 1],siz,1,1,1,true).max(CImg<doubleT>(&mem[pos + 1],siz,1,1,1,true));
              break;
            }
        }
      }