abc/src/base/io/ioReadPlaMo.c
// merge distance-1 with identical output part
merge distance-1 with identical output part
merge distance - 1 with identical output part
int Mop_ManMergeDist1Pairs( Mop_Man_t * p, Vec_Int_t * vGroup, Vec_Int_t * vGroupPrev, Vec_Int_t * vStats, int nLimit )
{
    Vec_Int_t * vPairs    = Mop_ManFindDist1Pairs( p, vGroup );
    Vec_Int_t * vPairsNew = Mop_ManCompatiblePairs( vPairs, Vec_IntSize(vGroup) );
    int nCubes = Vec_IntSize(vGroup) + Vec_IntSize(vGroupPrev);
    int w, i, c1, c2, iCubeNew, iVar;
    word * pCube, * pCube1, * pCube2;
    Vec_Int_t * vToFree = Vec_IntAlloc( Vec_IntSize(vPairsNew) );
    Vec_IntForEachEntryDouble( vPairsNew, c1, c2, i )
    {
        pCube1 = Mop_ManCubeIn( p, Vec_IntEntry(vGroup, c1) );
        pCube2 = Mop_ManCubeIn( p, Vec_IntEntry(vGroup, c2) );
        assert( Mop_ManCheckDist1(pCube1, pCube2, p->nWordsIn) );
        iVar = Mop_ManFindDiffVar( pCube1, pCube2, p->nWordsIn );
        if ( Vec_IntEntry( vStats, iVar ) > nLimit )
            continue;
        Vec_IntPush( vToFree, c1 );
        Vec_IntPush( vToFree, c2 );
        iCubeNew  = Vec_IntPop( p->vFree );
        pCube  = Mop_ManCubeIn( p, iCubeNew );
        for ( w = 0; w < p->nWordsIn; w++ )
            pCube[w] = pCube1[w] & pCube2[w];
        pCube  = Mop_ManCubeOut( p, iCubeNew );
        pCube1 = Mop_ManCubeOut( p, Vec_IntEntry(vGroup, c1) );
        pCube2 = Mop_ManCubeOut( p, Vec_IntEntry(vGroup, c2) );
        assert( !memcmp(pCube1, pCube2, sizeof(word)*p->nWordsOut) );
        for ( w = 0; w < p->nWordsOut; w++ )
            pCube[w] = pCube1[w];
        Vec_IntPush( vGroupPrev, iCubeNew );
    }
    Vec_IntForEachEntry( vToFree, c1, i )
    {
        if ( Vec_IntEntry(vGroup, c1) == -1 )
            continue;
        Vec_IntPush( p->vFree, Vec_IntEntry(vGroup, c1) );
        Vec_IntWriteEntry( vGroup, c1, -1 );
    }
    Vec_IntFree( vToFree );
    if ( Vec_IntSize(vPairsNew) > 0 )
        Map_ManGroupCompact( vGroup );
    Vec_IntFree( vPairs );
    Vec_IntFree( vPairsNew );
    return nCubes - Vec_IntSize(vGroup) - Vec_IntSize(vGroupPrev);
}
int Mop_ManMergeDist1Pairs ( Mop_Man_t * p , Vec_Int_t * vGroup , Vec_Int_t * vGroupPrev , Vec_Int_t * vStats , int nLimit ) { Vec_Int_t * vPairs = Mop_ManFindDist1Pairs ( p , vGroup ) ; Vec_Int_t * vPairsNew = Mop_ManCompatiblePairs ( vPairs , Vec_IntSize ( vGroup ) ) ; int nCubes = Vec_IntSize ( vGroup ) + Vec_IntSize ( vGroupPrev ) ; int w , i , c1 , c2 , iCubeNew , iVar ; word * pCube , * pCube1 , * pCube2 ; Vec_Int_t * vToFree = Vec_IntAlloc ( Vec_IntSize ( vPairsNew ) ) ; Vec_IntForEachEntryDouble ( vPairsNew , c1 , c2 , i ) { pCube1 = Mop_ManCubeIn ( p , Vec_IntEntry ( vGroup , c1 ) ) ; pCube2 = Mop_ManCubeIn ( p , Vec_IntEntry ( vGroup , c2 ) ) ; assert ( Mop_ManCheckDist1 ( pCube1 , pCube2 , p -> nWordsIn ) ) ; iVar = Mop_ManFindDiffVar ( pCube1 , pCube2 , p -> nWordsIn ) ; if ( Vec_IntEntry ( vStats , iVar ) > nLimit ) continue ; Vec_IntPush ( vToFree , c1 ) ; Vec_IntPush ( vToFree , c2 ) ; iCubeNew = Vec_IntPop ( p -> vFree ) ; pCube = Mop_ManCubeIn ( p , iCubeNew ) ; for ( w = 0 ; w < p -> nWordsIn ; w ++ ) pCube [ w ] = pCube1 [ w ] & pCube2 [ w ] ; pCube = Mop_ManCubeOut ( p , iCubeNew ) ; pCube1 = Mop_ManCubeOut ( p , Vec_IntEntry ( vGroup , c1 ) ) ; pCube2 = Mop_ManCubeOut ( p , Vec_IntEntry ( vGroup , c2 ) ) ; assert ( ! memcmp ( pCube1 , pCube2 , sizeof ( word ) * p -> nWordsOut ) ) ; for ( w = 0 ; w < p -> nWordsOut ; w ++ ) pCube [ w ] = pCube1 [ w ] ; Vec_IntPush ( vGroupPrev , iCubeNew ) ; } Vec_IntForEachEntry ( vToFree , c1 , i ) { if ( Vec_IntEntry ( vGroup , c1 ) == -1 ) continue ; Vec_IntPush ( p -> vFree , Vec_IntEntry ( vGroup , c1 ) ) ; Vec_IntWriteEntry ( vGroup , c1 , -1 ) ; } Vec_IntFree ( vToFree ) ; if ( Vec_IntSize ( vPairsNew ) > 0 ) Map_ManGroupCompact ( vGroup ) ; Vec_IntFree ( vPairs ) ; Vec_IntFree ( vPairsNew ) ; return nCubes - Vec_IntSize ( vGroup ) - Vec_IntSize ( vGroupPrev ) ; }
merge distance-1 with identical output part
merge distance - 1 with identical output part
// move cubes to the previous group // skip those cubes that have frequently appearing variables //    Vec_IntForEachEntry( vPairsNew, c1, i )