LCOV - code coverage report
Current view: top level - sc/source/core/data - markarr.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 175 190 92.1 %
Date: 2012-08-25 Functions: 14 14 100.0 %
Legend: Lines: hit not hit | Branches: + taken - not taken # not executed Branches: 109 144 75.7 %

           Branch data     Line data    Source code
       1                 :            : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2                 :            : /*************************************************************************
       3                 :            :  *
       4                 :            :  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
       5                 :            :  *
       6                 :            :  * Copyright 2000, 2010 Oracle and/or its affiliates.
       7                 :            :  *
       8                 :            :  * OpenOffice.org - a multi-platform office productivity suite
       9                 :            :  *
      10                 :            :  * This file is part of OpenOffice.org.
      11                 :            :  *
      12                 :            :  * OpenOffice.org is free software: you can redistribute it and/or modify
      13                 :            :  * it under the terms of the GNU Lesser General Public License version 3
      14                 :            :  * only, as published by the Free Software Foundation.
      15                 :            :  *
      16                 :            :  * OpenOffice.org is distributed in the hope that it will be useful,
      17                 :            :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      18                 :            :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      19                 :            :  * GNU Lesser General Public License version 3 for more details
      20                 :            :  * (a copy is included in the LICENSE file that accompanied this code).
      21                 :            :  *
      22                 :            :  * You should have received a copy of the GNU Lesser General Public License
      23                 :            :  * version 3 along with OpenOffice.org.  If not, see
      24                 :            :  * <http://www.openoffice.org/license.html>
      25                 :            :  * for a copy of the LGPLv3 License.
      26                 :            :  *
      27                 :            :  ************************************************************************/
      28                 :            : 
      29                 :            : #include "markarr.hxx"
      30                 :            : #include "global.hxx"
      31                 :            : #include "address.hxx"
      32                 :            : 
      33                 :            : // STATIC DATA -----------------------------------------------------------
      34                 :            : 
      35                 :            : //------------------------------------------------------------------------
      36                 :            : 
      37                 :     673792 : ScMarkArray::ScMarkArray() :
      38                 :            :     nCount( 0 ),
      39                 :            :     nLimit( 0 ),
      40                 :     673792 :     pData( NULL )
      41                 :            : {
      42                 :            :     // special case "no marks" with pData = NULL
      43                 :     673792 : }
      44                 :            : 
      45                 :            : //------------------------------------------------------------------------
      46                 :            : 
      47                 :     671744 : ScMarkArray::~ScMarkArray()
      48                 :            : {
      49         [ +  + ]:     671744 :     delete[] pData;
      50                 :     671744 : }
      51                 :            : 
      52                 :            : //------------------------------------------------------------------------
      53                 :            : 
      54                 :      11684 : void ScMarkArray::Reset( sal_Bool bMarked )
      55                 :            : {
      56                 :            :     // always create pData here
      57                 :            :     // (or have separate method to ensure pData)
      58                 :            : 
      59         [ +  + ]:      11684 :     delete[] pData;
      60                 :            : 
      61                 :      11684 :     nCount = nLimit = 1;
      62                 :      11684 :     pData = new ScMarkEntry[1];
      63                 :      11684 :     pData[0].nRow = MAXROW;
      64                 :      11684 :     pData[0].bMarked = bMarked;
      65                 :      11684 : }
      66                 :            : 
      67                 :            : //------------------------------------------------------------------------
      68                 :            : 
      69                 :       8818 : sal_Bool ScMarkArray::Search( SCROW nRow, SCSIZE& nIndex ) const
      70                 :            : {
      71                 :       8818 :     long    nHi         = static_cast<long>(nCount) - 1;
      72                 :       8818 :     long    i           = 0;
      73                 :       8818 :     sal_Bool    bFound      = (nCount == 1);
      74         [ +  + ]:       8818 :     if (pData)
      75                 :            :     {
      76                 :       8607 :         long    nLo         = 0;
      77                 :       8607 :         long    nStartRow   = 0;
      78 [ +  + ][ +  - ]:      20167 :         while ( !bFound && nLo <= nHi )
                 [ +  + ]
      79                 :            :         {
      80                 :      11560 :             i = (nLo + nHi) / 2;
      81         [ +  + ]:      11560 :             if (i > 0)
      82                 :       7939 :                 nStartRow = (long) pData[i - 1].nRow;
      83                 :            :             else
      84                 :       3621 :                 nStartRow = -1;
      85                 :      11560 :             long nEndRow = (long) pData[i].nRow;
      86         [ +  + ]:      11560 :             if (nEndRow < (long) nRow)
      87                 :       5751 :                 nLo = ++i;
      88                 :            :             else
      89         [ +  + ]:       5809 :                 if (nStartRow >= (long) nRow)
      90                 :         90 :                     nHi = --i;
      91                 :            :                 else
      92                 :       5719 :                     bFound = sal_True;
      93                 :            :         }
      94                 :            :     }
      95                 :            :     else
      96                 :        211 :         bFound = false;
      97                 :            : 
      98         [ +  + ]:       8818 :     if (bFound)
      99                 :       8607 :         nIndex=(SCSIZE)i;
     100                 :            :     else
     101                 :        211 :         nIndex=0;
     102                 :       8818 :     return bFound;
     103                 :            : }
     104                 :            : 
     105                 :       1036 : sal_Bool ScMarkArray::GetMark( SCROW nRow ) const
     106                 :            : {
     107                 :            :     SCSIZE i;
     108         [ +  + ]:       1036 :     if (Search( nRow, i ))
     109                 :        915 :         return pData[i].bMarked;
     110                 :            :     else
     111                 :       1036 :         return false;
     112                 :            : 
     113                 :            : }
     114                 :            : 
     115                 :            : //------------------------------------------------------------------------
     116                 :            : 
     117                 :      16962 : void ScMarkArray::SetMarkArea( SCROW nStartRow, SCROW nEndRow, sal_Bool bMarked )
     118                 :            : {
     119 [ +  - ][ +  - ]:      16962 :     if (ValidRow(nStartRow) && ValidRow(nEndRow))
                 [ +  - ]
     120                 :            :     {
     121 [ +  + ][ +  + ]:      16962 :         if ((nStartRow == 0) && (nEndRow == MAXROW))
     122                 :            :         {
     123                 :       8192 :             Reset(bMarked);
     124                 :            :         }
     125                 :            :         else
     126                 :            :         {
     127         [ +  + ]:       8770 :             if (!pData)
     128                 :       3490 :                 Reset(false);   // create pData for further processing - could use special case handling!
     129                 :            : 
     130                 :       8770 :             SCSIZE nNeeded = nCount + 2;
     131         [ +  + ]:       8770 :             if ( nLimit < nNeeded )
     132                 :            :             {
     133                 :       3928 :                 nLimit += SC_MARKARRAY_DELTA;
     134         [ -  + ]:       3928 :                 if ( nLimit < nNeeded )
     135                 :          0 :                     nLimit = nNeeded;
     136                 :       3928 :                 ScMarkEntry* pNewData = new ScMarkEntry[nLimit];
     137                 :       3928 :                 memcpy( pNewData, pData, nCount*sizeof(ScMarkEntry) );
     138         [ +  - ]:       3928 :                 delete[] pData;
     139                 :       3928 :                 pData = pNewData;
     140                 :            :             }
     141                 :            : 
     142                 :            :             SCSIZE ni;          // number of entries in beginning
     143                 :            :             SCSIZE nInsert;     // insert position (MAXROW+1 := no insert)
     144                 :       8770 :             sal_Bool bCombined = false;
     145                 :       8770 :             sal_Bool bSplit = false;
     146         [ +  + ]:       8770 :             if ( nStartRow > 0 )
     147                 :            :             {
     148                 :            :                 // skip beginning
     149                 :            :                 SCSIZE nIndex;
     150                 :       5489 :                 Search( nStartRow, nIndex );
     151                 :       5489 :                 ni = nIndex;
     152                 :            : 
     153                 :       5489 :                 nInsert = MAXROWCOUNT;
     154         [ +  + ]:       5489 :                 if ( pData[ni].bMarked != bMarked )
     155                 :            :                 {
     156 [ +  + ][ +  + ]:       5424 :                     if ( ni == 0 || (pData[ni-1].nRow < nStartRow - 1) )
     157                 :            :                     {   // may be a split or a simple insert or just a shrink,
     158                 :            :                         // row adjustment is done further down
     159         [ +  - ]:       1720 :                         if ( pData[ni].nRow > nEndRow )
     160                 :       1720 :                             bSplit = sal_True;
     161                 :       1720 :                         ni++;
     162                 :       1720 :                         nInsert = ni;
     163                 :            :                     }
     164 [ +  - ][ +  - ]:       3704 :                     else if ( ni > 0 && pData[ni-1].nRow == nStartRow - 1 )
     165                 :       5424 :                         nInsert = ni;
     166                 :            :                 }
     167 [ +  - ][ +  + ]:       5489 :                 if ( ni > 0 && pData[ni-1].bMarked == bMarked )
     168                 :            :                 {   // combine
     169                 :       3704 :                     pData[ni-1].nRow = nEndRow;
     170                 :       3704 :                     nInsert = MAXROWCOUNT;
     171                 :       5489 :                     bCombined = sal_True;
     172                 :            :                 }
     173                 :            :             }
     174                 :            :             else
     175                 :            :         {
     176                 :       3281 :                 nInsert = 0;
     177                 :       3281 :                 ni = 0;
     178                 :            :         }
     179                 :            : 
     180                 :       8770 :             SCSIZE nj = ni;     // stop position of range to replace
     181 [ +  + ][ +  + ]:       9478 :             while ( nj < nCount && pData[nj].nRow <= nEndRow )
                 [ +  + ]
     182                 :        708 :                 nj++;
     183         [ +  + ]:       8770 :             if ( !bSplit )
     184                 :            :             {
     185 [ +  - ][ +  + ]:       7050 :                 if ( nj < nCount && pData[nj].bMarked == bMarked )
     186                 :            :                 {   // combine
     187         [ +  + ]:       1082 :                     if ( ni > 0 )
     188                 :            :                     {
     189         [ +  + ]:         52 :                         if ( pData[ni-1].bMarked == bMarked )
     190                 :            :                         {   // adjacent entries
     191                 :         42 :                             pData[ni-1].nRow = pData[nj].nRow;
     192                 :         42 :                             nj++;
     193                 :            :                         }
     194         [ -  + ]:         10 :                         else if ( ni == nInsert )
     195                 :          0 :                             pData[ni-1].nRow = nStartRow - 1;   // shrink
     196                 :            :                     }
     197                 :       1082 :                     nInsert = MAXROWCOUNT;
     198                 :       1082 :                     bCombined = sal_True;
     199                 :            :                 }
     200 [ +  + ][ -  + ]:       5968 :                 else if ( ni > 0 && ni == nInsert )
     201                 :       7050 :                     pData[ni-1].nRow = nStartRow - 1;   // shrink
     202                 :            :             }
     203         [ +  + ]:       8770 :             if ( ni < nj )
     204                 :            :             {   // remove middle entries
     205         [ +  + ]:        708 :                 if ( !bCombined )
     206                 :            :                 {   // replace one entry
     207                 :        654 :                     pData[ni].nRow = nEndRow;
     208                 :        654 :                     pData[ni].bMarked = bMarked;
     209                 :        654 :                     ni++;
     210                 :        654 :                     nInsert = MAXROWCOUNT;
     211                 :            :                 }
     212         [ +  + ]:        708 :                 if ( ni < nj )
     213                 :            :                 {   // remove entries
     214                 :         54 :                     memmove( pData + ni, pData + nj, (nCount - nj) * sizeof(ScMarkEntry) );
     215                 :         54 :                     nCount -= nj - ni;
     216                 :            :                 }
     217                 :            :             }
     218                 :            : 
     219         [ +  + ]:       8770 :             if ( nInsert < sal::static_int_cast<SCSIZE>(MAXROWCOUNT) )
     220                 :            :             {   // insert or append new entry
     221         [ +  - ]:       3372 :                 if ( nInsert <= nCount )
     222                 :            :                 {
     223         [ +  + ]:       3372 :                     if ( !bSplit )
     224                 :       1652 :                         memmove( pData + nInsert + 1, pData + nInsert,
     225                 :       1652 :                             (nCount - nInsert) * sizeof(ScMarkEntry) );
     226                 :            :                     else
     227                 :            :                     {
     228                 :       1720 :                         memmove( pData + nInsert + 2, pData + nInsert,
     229                 :       3440 :                             (nCount - nInsert) * sizeof(ScMarkEntry) );
     230                 :       1720 :                         pData[nInsert+1] = pData[nInsert-1];
     231                 :       1720 :                         nCount++;
     232                 :            :                     }
     233                 :            :                 }
     234         [ +  + ]:       3372 :                 if ( nInsert )
     235                 :       1720 :                     pData[nInsert-1].nRow = nStartRow - 1;
     236                 :       3372 :                 pData[nInsert].nRow = nEndRow;
     237                 :       3372 :                 pData[nInsert].bMarked = bMarked;
     238                 :      16962 :                 nCount++;
     239                 :            :             }
     240                 :            :         }
     241                 :            :     }
     242                 :      16962 : }
     243                 :            : 
     244                 :         36 : sal_Bool ScMarkArray::IsAllMarked( SCROW nStartRow, SCROW nEndRow ) const
     245                 :            : {
     246                 :            :     SCSIZE nStartIndex;
     247                 :            :     SCSIZE nEndIndex;
     248                 :            : 
     249         [ +  - ]:         36 :     if (Search( nStartRow, nStartIndex ))
     250         [ +  - ]:         36 :         if (pData[nStartIndex].bMarked)
     251         [ +  - ]:         36 :             if (Search( nEndRow, nEndIndex ))
     252         [ +  - ]:         36 :                 if (nEndIndex==nStartIndex)
     253                 :         36 :                     return sal_True;
     254                 :            : 
     255                 :         36 :     return false;
     256                 :            : }
     257                 :            : 
     258                 :        456 : sal_Bool ScMarkArray::HasOneMark( SCROW& rStartRow, SCROW& rEndRow ) const
     259                 :            : {
     260                 :        456 :     sal_Bool bRet = false;
     261         [ -  + ]:        456 :     if ( nCount == 1 )
     262                 :            :     {
     263         [ #  # ]:          0 :         if ( pData[0].bMarked )
     264                 :            :         {
     265                 :          0 :             rStartRow = 0;
     266                 :          0 :             rEndRow = MAXROW;
     267                 :          0 :             bRet = sal_True;
     268                 :            :         }
     269                 :            :     }
     270         [ +  + ]:        456 :     else if ( nCount == 2 )
     271                 :            :     {
     272         [ +  - ]:        424 :         if ( pData[0].bMarked )
     273                 :            :         {
     274                 :        424 :             rStartRow = 0;
     275                 :        424 :             rEndRow = pData[0].nRow;
     276                 :            :         }
     277                 :            :         else
     278                 :            :         {
     279                 :          0 :             rStartRow = pData[0].nRow + 1;
     280                 :          0 :             rEndRow = MAXROW;
     281                 :            :         }
     282                 :        424 :         bRet = sal_True;
     283                 :            :     }
     284         [ +  - ]:         32 :     else if ( nCount == 3 )
     285                 :            :     {
     286         [ +  - ]:         32 :         if ( pData[1].bMarked )
     287                 :            :         {
     288                 :         32 :             rStartRow = pData[0].nRow + 1;
     289                 :         32 :             rEndRow = pData[1].nRow;
     290                 :         32 :             bRet = sal_True;
     291                 :            :         }
     292                 :            :     }
     293                 :        456 :     return bRet;
     294                 :            : }
     295                 :            : 
     296                 :     165888 : void ScMarkArray::CopyMarksTo( ScMarkArray& rDestMarkArray ) const
     297                 :            : {
     298         [ -  + ]:     165888 :     delete[] rDestMarkArray.pData;
     299                 :            : 
     300         [ +  + ]:     165888 :     if (pData)
     301                 :            :     {
     302                 :       1999 :         rDestMarkArray.pData = new ScMarkEntry[nCount];
     303                 :       1999 :         memmove( rDestMarkArray.pData, pData, nCount * sizeof(ScMarkEntry) );
     304                 :            :     }
     305                 :            :     else
     306                 :     163889 :         rDestMarkArray.pData = NULL;
     307                 :            : 
     308                 :     165888 :     rDestMarkArray.nCount = rDestMarkArray.nLimit = nCount;
     309                 :     165888 : }
     310                 :            : 
     311                 :       1029 : SCsROW ScMarkArray::GetNextMarked( SCsROW nRow, sal_Bool bUp ) const
     312                 :            : {
     313         [ +  + ]:       1029 :     if (!pData)
     314                 :          2 :         const_cast<ScMarkArray*>(this)->Reset(false);   // create pData for further processing
     315                 :            : 
     316                 :       1029 :     SCsROW nRet = nRow;
     317         [ +  - ]:       1029 :     if (VALIDROW(nRow))
     318                 :            :     {
     319                 :            :         SCSIZE nIndex;
     320                 :       1029 :         Search(nRow, nIndex);
     321         [ +  + ]:       1029 :         if (!pData[nIndex].bMarked)
     322                 :            :         {
     323         [ -  + ]:          2 :             if (bUp)
     324                 :            :             {
     325         [ #  # ]:          0 :                 if (nIndex>0)
     326                 :          0 :                     nRet = pData[nIndex-1].nRow;
     327                 :            :                 else
     328                 :          0 :                     nRet = -1;
     329                 :            :             }
     330                 :            :             else
     331                 :       1029 :                 nRet = pData[nIndex].nRow + 1;
     332                 :            :         }
     333                 :            :     }
     334                 :       1029 :     return nRet;
     335                 :            : }
     336                 :            : 
     337                 :       1027 : SCROW ScMarkArray::GetMarkEnd( SCROW nRow, sal_Bool bUp ) const
     338                 :            : {
     339         [ -  + ]:       1027 :     if (!pData)
     340         [ #  # ]:          0 :         const_cast<ScMarkArray*>(this)->Reset(false);   // create pData for further processing
     341                 :            : 
     342                 :            :     SCROW nRet;
     343                 :            :     SCSIZE nIndex;
     344                 :       1027 :     Search(nRow, nIndex);
     345                 :            :     OSL_ENSURE( pData[nIndex].bMarked, "GetMarkEnd ohne bMarked" );
     346         [ -  + ]:       1027 :     if (bUp)
     347                 :            :     {
     348         [ #  # ]:          0 :         if (nIndex>0)
     349                 :          0 :             nRet = pData[nIndex-1].nRow + 1;
     350                 :            :         else
     351                 :          0 :             nRet = 0;
     352                 :            :     }
     353                 :            :     else
     354                 :       1027 :         nRet = pData[nIndex].nRow;
     355                 :            : 
     356                 :       1027 :     return nRet;
     357                 :            : }
     358                 :            : 
     359                 :            : //
     360                 :            : //  -------------- Iterator ----------------------------------------------
     361                 :            : //
     362                 :            : 
     363                 :     543583 : ScMarkArrayIter::ScMarkArrayIter( const ScMarkArray* pNewArray ) :
     364                 :            :     pArray( pNewArray ),
     365                 :     543583 :     nPos( 0 )
     366                 :            : {
     367                 :     543583 : }
     368                 :            : 
     369                 :     543583 : ScMarkArrayIter::~ScMarkArrayIter()
     370                 :            : {
     371                 :     543583 : }
     372                 :            : 
     373                 :     551047 : sal_Bool ScMarkArrayIter::Next( SCROW& rTop, SCROW& rBottom )
     374                 :            : {
     375         [ +  + ]:     551047 :     if ( nPos >= pArray->nCount )
     376                 :     539037 :         return false;
     377         [ +  + ]:      15574 :     while (!pArray->pData[nPos].bMarked)
     378                 :            :     {
     379                 :       7790 :         ++nPos;
     380         [ +  + ]:       7790 :         if ( nPos >= pArray->nCount )
     381                 :       4226 :             return false;
     382                 :            :     }
     383                 :       7784 :     rBottom = pArray->pData[nPos].nRow;
     384         [ +  + ]:       7784 :     if (nPos==0)
     385                 :       4220 :         rTop = 0;
     386                 :            :     else
     387                 :       3564 :         rTop = pArray->pData[nPos-1].nRow + 1;
     388                 :       7784 :     ++nPos;
     389                 :     551047 :     return sal_True;
     390                 :            : }
     391                 :            : 
     392                 :            : 
     393                 :            : 
     394                 :            : 
     395                 :            : 
     396                 :            : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10