Пример #1
0
        public void TestExtraStringRecord_bug46213()
        {
            FormulaRecord fr = new FormulaRecord();
            fr.Value = (2.0);
            StringRecord sr = new StringRecord();
            sr.String = ("NA");
            SharedValueManager svm = SharedValueManager.CreateEmpty();
            FormulaRecordAggregate fra;

            try
            {
                fra = new FormulaRecordAggregate(fr, sr, svm);
            }
            catch (RecordFormatException e)
            {
                if ("String record was  supplied but formula record flag is not  set".Equals(e.Message))
                {
                    throw new AssertionException("Identified bug 46213");
                }
                throw e;
            }
            TestCases.HSSF.UserModel.RecordInspector.RecordCollector rc = new TestCases.HSSF.UserModel.RecordInspector.RecordCollector();
            fra.VisitContainedRecords(rc);
            Record[] vraRecs = rc.Records;
            Assert.AreEqual(1, vraRecs.Length);
            Assert.AreEqual(fr, vraRecs[0]);
        }
Пример #2
0
        public void TestCheckNanPreserve()
        {
            byte[] formulaByte = new byte[29];

            formulaByte[4] = (byte)0x0F;
            formulaByte[6] = (byte)0x02;
            formulaByte[8] = (byte)0x07;
            formulaByte[12] = (byte)0xFF;
            formulaByte[13] = (byte)0xFF;
            formulaByte[18] = (byte)0xE0;
            formulaByte[19] = (byte)0xFC;
            formulaByte[20] = (byte)0x07;
            formulaByte[22] = (byte)0x1E;
            formulaByte[23] = (byte)0x01;
            formulaByte[25] = (byte)0x1E;
            formulaByte[28] = (byte)0x06;

            FormulaRecord record = new FormulaRecord(TestcaseRecordInputStream.Create(FormulaRecord.sid,  formulaByte));
            Assert.AreEqual(0, record.Row, "Row");
            Assert.AreEqual(0, record.Column, "Column");
            Assert.AreEqual(record.CachedResultType,NPOI.SS.UserModel.CellType.ERROR);

            byte[] output = record.Serialize();
            Assert.AreEqual(33, output.Length, "Output size"); //includes sid+recordlength

            for (int i = 5; i < 13; i++)
            {
                Assert.AreEqual(formulaByte[i], output[i + 4], "FormulaByte NaN doesn't match");
            }
        }
Пример #3
0
 public void TestBasic()
 {
     FormulaRecord f = new FormulaRecord();
     f.SetCachedResultTypeString();
     StringRecord s = new StringRecord();
     s.String = ("abc");
     FormulaRecordAggregate fagg = new FormulaRecordAggregate(f, s, SharedValueManager.CreateEmpty());
     Assert.AreEqual("abc", fagg.StringValue);
 }
Пример #4
0
        public override Object Clone()
        {
            FormulaRecord rec = new FormulaRecord();

            CopyBaseFields(rec);
            rec.field_4_value       = field_4_value;
            rec.field_5_options     = field_5_options;
            rec.field_6_zero        = field_6_zero;
            rec.field_8_parsed_expr = field_8_parsed_expr.Copy();
            rec.specialCachedValue  = specialCachedValue;
            return(rec);
        }
Пример #5
0
        /**
         * @return the equivalent {@link Ptg} array that the formula would have, were it not shared.
         */
        public Ptg[] GetFormulaTokens(FormulaRecord formula)
        {
            int formulaRow    = formula.Row;
            int formulaColumn = formula.Column;

            //Sanity checks
            if (!IsInRange(formulaRow, formulaColumn))
            {
                throw new Exception("Shared Formula Conversion: Coding Error");
            }

            return(ConvertSharedFormulas(field_7_parsed_expr.Tokens, formulaRow, formulaColumn));
        }
Пример #6
0
        public void TestCreateFormulaRecord()
        {
            FormulaRecord record = new FormulaRecord();
            record.Column=((short)0);
            //record.SetRow((short)1);
            record.Row=(1);
            record.XFIndex=((short)4);

            Assert.AreEqual(record.Column, (short)0);
            //Assert.AreEqual(record.Row,(short)1);
            Assert.AreEqual((short)record.Row, (short)1);
            Assert.AreEqual(record.XFIndex, (short)4);
        }
Пример #7
0
        /**
         * @return the equivalent {@link Ptg} array that the formula would have, were it not shared.
         */
        public Ptg[] GetFormulaTokens(FormulaRecord formula)
        {
            int formulaRow    = formula.Row;
            int formulaColumn = formula.Column;

            //Sanity checks
            if (!IsInRange(formulaRow, formulaColumn))
            {
                throw new Exception("Shared Formula Conversion: Coding Error");
            }
            SharedFormula sf = new SharedFormula(SpreadsheetVersion.EXCEL97);

            return(sf.ConvertSharedFormulas(field_7_parsed_expr.Tokens, formulaRow, formulaColumn));
            //return ConvertSharedFormulas(field_7_parsed_expr.Tokens, formulaRow, formulaColumn);
        }
Пример #8
0
 private IList TestData()
 {
     IList records = new ArrayList();
     FormulaRecord formulaRecord = new FormulaRecord();
     //UnknownRecord unknownRecord = new UnknownRecord();
     BlankRecord blankRecord = new BlankRecord();
     WindowOneRecord windowOneRecord = new WindowOneRecord();
     formulaRecord.Row = 1;
     formulaRecord.Column = 1;
     blankRecord.Row = 2;
     blankRecord.Column = 2;
     records.Add(formulaRecord);
     records.Add(blankRecord);
     records.Add(windowOneRecord);
     return records;
 }
Пример #9
0
 public void ConvertSharedFormulaRecord(FormulaRecord formula)
 {
     int row = formula.Row;
     int column = formula.Column;
     // Traverse the list of shared formulas in
     // reverse order, and try to find the correct one
     // for us
     for (int i = 0; i < _sfrs.Length; i++)
     {
         SharedFormulaRecord shrd = _sfrs[i];
         if (shrd.IsInRange(row, column))
         {
             shrd.ConvertSharedFormulaRecord(formula);
             return;
         }
     }
     // not found
     handleMissingSharedFormulaRecord(formula);
 }
        /// <summary>
        /// Initializes a new instance of the <see cref="FormulaRecordAggregate"/> class.
        /// </summary>
        /// <param name="formulaRec">The formula rec.</param>
        /// <param name="stringRec">The string rec.</param>
        /// <param name="svm">The SVM.</param>
        public FormulaRecordAggregate(FormulaRecord formulaRec, StringRecord stringRec, SharedValueManager svm)
        {
            if (svm == null)
            {
                throw new ArgumentException("sfm must not be null");
            }
            bool hasStringRec = stringRec != null;
            bool hasCachedStringFlag = formulaRec.HasCachedResultString;
            if (hasStringRec != hasCachedStringFlag)
            {
                throw new RecordFormatException("String record was "
                        + (hasStringRec ? "" : "not ") + " supplied but formula record flag is "
                        + (hasCachedStringFlag ? "" : "not ") + " set");
            }

            if (formulaRec.IsSharedFormula)
            {
                svm.ConvertSharedFormulaRecord(formulaRec);
            }
            _formulaRecord = formulaRec;
            _sharedValueManager = svm;
            _stringRecord = stringRec;
        }
        /// <summary>
        /// Initializes a new instance of the <see cref="FormulaRecordAggregate"/> class.
        /// </summary>
        /// <param name="formulaRec">The formula rec.</param>
        /// <param name="stringRec">The string rec.</param>
        /// <param name="svm">The SVM.</param>
        public FormulaRecordAggregate(FormulaRecord formulaRec, StringRecord stringRec, SharedValueManager svm)
        {
            if (svm == null)
            {
                throw new ArgumentException("sfm must not be null");
            }
            if (formulaRec.HasCachedResultString)
            {
                if (stringRec == null)
                {
                    throw new RecordFormatException("Formula record flag is set but String record was not found");
                }
                _stringRecord = stringRec;
            }
            else
            {
                // Usually stringRec is null here (in agreement with what the formula rec says).
                // In the case where an extra StringRecord is erroneously present, Excel (2007)
                // ignores it (see bug 46213).
                _stringRecord = null;
            }

            _formulaRecord = formulaRec;
            _sharedValueManager = svm;
            if (formulaRec.IsSharedFormula)
            {
                CellReference firstCell = formulaRec.Formula.ExpReference;
                if (firstCell == null)
                {
                    HandleMissingSharedFormulaRecord(formulaRec);
                }
                else
                {
                    _sharedFormulaRecord = svm.LinkSharedFormulaRecord(firstCell, this);
                }
            }
        }
Пример #12
0
        public void TestRowAggregation()
        {
            ArrayList records = new ArrayList();

            records.Add(InternalSheet.CreateBOF());
            records.Add(new DimensionsRecord());
            records.Add(new RowRecord(0));
            records.Add(new RowRecord(1));
            FormulaRecord formulaRecord = new FormulaRecord();
            formulaRecord.SetCachedResultTypeString();
            records.Add(formulaRecord);
            records.Add(new StringRecord());
            records.Add(new RowRecord(2));
            records.Add(CreateWindow2Record());
            records.Add(EOFRecord.instance);

            InternalSheet sheet = CreateSheet(records);
            Assert.IsNotNull(sheet.GetRow(2), "Row [2] was skipped");
        }
Пример #13
0
        /**
         * @return the equivalent {@link Ptg} array that the formula would have, were it not shared.
         */
        public Ptg[] GetFormulaTokens(FormulaRecord formula)
        {
            int formulaRow = formula.Row;
            int formulaColumn = formula.Column;
            //Sanity checks
            if (!IsInRange(formulaRow, formulaColumn))
            {
                throw new Exception("Shared Formula Conversion: Coding Error");
            }

            return ConvertSharedFormulas(field_7_parsed_expr.Tokens, formulaRow, formulaColumn);
        }
Пример #14
0
        public void TestArrayFormulas()
        {
            int rownum = 4;
            int colnum = 4;

            FormulaRecord fr = new FormulaRecord();
            fr.Row=(rownum);
            fr.Column=((short)colnum);

            FormulaRecordAggregate agg = new FormulaRecordAggregate(fr, null, SharedValueManager.CreateEmpty());
            Ptg[] ptgsForCell = { new ExpPtg(rownum, colnum) };
            agg.SetParsedExpression(ptgsForCell);

            String formula = "SUM(A1:A3*B1:B3)";
            Ptg[] ptgs = HSSFFormulaParser.Parse(formula, null, FormulaType.ARRAY, 0);
            agg.SetArrayFormula(new CellRangeAddress(rownum, rownum, colnum, colnum), ptgs);

            Assert.IsTrue(agg.IsPartOfArrayFormula);
            Assert.AreEqual("E5", agg.GetArrayFormulaRange().FormatAsString());
            Ptg[] ptg = agg.FormulaTokens;
            String fmlaSer = FormulaRenderer.ToFormulaString(null, ptg);
            Assert.AreEqual(formula, fmlaSer);

            agg.RemoveArrayFormula(rownum, colnum);
            Assert.IsFalse(agg.IsPartOfArrayFormula);
        }
Пример #15
0
 /// <summary>
 /// Checks the type of the formula cached value.
 /// </summary>
 /// <param name="expectedTypeCode">The expected type code.</param>
 /// <param name="fr">The fr.</param>
 private void CheckFormulaCachedValueType(CellType expectedTypeCode, FormulaRecord fr)
 {
     CellType cachedValueType = fr.CachedResultType;
     if (cachedValueType != expectedTypeCode)
     {
         throw TypeMismatch(expectedTypeCode, cachedValueType, true);
     }
 }
Пример #16
0
 /**
  * Sometimes the shared formula flag "seems" to be erroneously set, in which case there is no 
  * call to <tt>SharedFormulaRecord.convertSharedFormulaRecord</tt> and hence the 
  * <tt>parsedExpression</tt> field of this <tt>FormulaRecord</tt> will not get updated.<br/>
  * As it turns out, this is not a problem, because in these circumstances, the existing value
  * for <tt>parsedExpression</tt> is perfectly OK.<p/>
  * 
  * This method may also be used for setting breakpoints to help diagnose issues regarding the
  * abnormally-set 'shared formula' flags. 
  * (see TestValueRecordsAggregate.testSpuriousSharedFormulaFlag()).<p/>
  * 
  * The method currently does nothing but do not delete it without finding a nice home for this 
  * comment.
  */
 private static void handleMissingSharedFormulaRecord(FormulaRecord formula)
 {
     // could log an info message here since this is a fairly unusual occurrence.
     formula.IsSharedFormula=(false); // no point leaving the flag erroneously set
 }
Пример #17
0
 public FormulaRecordAggregate CreateFormula(int row, int col)
 {
     FormulaRecord fr = new FormulaRecord();
     fr.Row=(row);
     fr.Column=((short)col);
     return new FormulaRecordAggregate(fr, null, _sharedValueManager);
 }
Пример #18
0
 public override Object Clone()
 {
     FormulaRecord rec = new FormulaRecord();
     CopyBaseFields(rec);
     rec.field_4_value = field_4_value;
     rec.field_5_options = field_5_options;
     rec.field_6_zero = field_6_zero;
     rec.field_8_parsed_expr = field_8_parsed_expr.Copy();
     rec.specialCachedValue = specialCachedValue;
     return rec;
 }
Пример #19
0
        public void TestWithConcat()
        {
            // =CHOOSE(2,A2,A3,A4)
            byte[] data = {
				6, 0, 68, 0,
				1, 0, 1, 0, 15, 0, 0, 0, 0, 0, 0, 0, 57,
				64, 0, 0, 12, 0, 12, unchecked((byte)-4), 46, 0, 
				30, 2, 0,	// Int - 2
				25, 4, 3, 0, // Attr
					8, 0, 17, 0, 26, 0, // jumpTable
					35, 0, // chooseOffSet
				36, 1, 0, 0, unchecked((byte)-64), // Ref - A2
				25, 8, 21, 0, // Attr
				36, 2, 0, 0, unchecked((byte)-64), // Ref - A3
				25,	8, 12, 0, // Attr
				36, 3, 0, 0, unchecked((byte)-64), // Ref - A4
				25, 8, 3, 0,  // Attr 
				66, 4, 100, 0 // CHOOSE
		    };
            RecordInputStream inp = new RecordInputStream(new MemoryStream(data));
            inp.NextRecord();

            FormulaRecord fr = new FormulaRecord(inp);

            Ptg[] ptgs = fr.ParsedExpression;
            Assert.AreEqual(9, ptgs.Length);
            Assert.AreEqual(typeof(IntPtg), ptgs[0].GetType());
            Assert.AreEqual(typeof(AttrPtg), ptgs[1].GetType());
            Assert.AreEqual(typeof(RefPtg), ptgs[2].GetType());
            Assert.AreEqual(typeof(AttrPtg), ptgs[3].GetType());
            Assert.AreEqual(typeof(RefPtg), ptgs[4].GetType());
            Assert.AreEqual(typeof(AttrPtg), ptgs[5].GetType());
            Assert.AreEqual(typeof(RefPtg), ptgs[6].GetType());
            Assert.AreEqual(typeof(AttrPtg), ptgs[7].GetType());
            Assert.AreEqual(typeof(FuncVarPtg), ptgs[8].GetType());

            FuncVarPtg choose = (FuncVarPtg)ptgs[8];
            Assert.AreEqual("CHOOSE", choose.Name);
        }
Пример #20
0
 /**
  * Note - does not return SharedFormulaRecords currently, because the corresponding formula
  * records have been converted to 'unshared'. POI does not attempt to re-share formulas. On
  * the other hand, there is no such conversion for array or table formulas, so this method 
  * returns the TABLE or ARRAY record (if it should be written after the specified 
  * formulaRecord.
  * 
  * @return the TABLE or ARRAY record for this formula cell, if it is the first cell of a 
  * table or array region.
  */
 public SharedValueRecordBase GetRecordForFirstCell(FormulaRecord formulaRecord)
 {
     int row = formulaRecord.Row;
     int column = formulaRecord.Column;
     for (int i = 0; i < _tableRecords.Length; i++)
     {
         TableRecord tr = _tableRecords[i];
         if (tr.IsFirstCell(row, column))
         {
             return tr;
         }
     }
     for (int i = 0; i < _arrayRecords.Length; i++)
     {
         ArrayRecord ar = _arrayRecords[i];
         if (ar.IsFirstCell(row, column))
         {
             return ar;
         }
     }
     return null;
 }
Пример #21
0
        public void TestReSerialize()
        {
            FormulaRecord formulaRecord = new FormulaRecord();
            formulaRecord.Row = (/*setter*/1);
            formulaRecord.Column = (/*setter*/(short)1);
            formulaRecord.ParsedExpression = (/*setter*/new Ptg[] { new RefPtg("B$5"), });
            formulaRecord.Value = (/*setter*/3.3);
            byte[] ser = formulaRecord.Serialize();
            Assert.AreEqual(31, ser.Length);

            RecordInputStream in1 = TestcaseRecordInputStream.Create(ser);
            FormulaRecord fr2 = new FormulaRecord(in1);
            Assert.AreEqual(3.3, fr2.Value, 0.0);
            Ptg[] ptgs = fr2.ParsedExpression;
            Assert.AreEqual(1, ptgs.Length);
            RefPtg rp = (RefPtg)ptgs[0];
            Assert.AreEqual("B$5", rp.ToFormulaString());
        }
Пример #22
0
 public override Object Clone()
 {
     FormulaRecord rec = new FormulaRecord();
     rec.field_1_row = field_1_row;
     rec.field_2_column = field_2_column;
     rec.field_3_xf = field_3_xf;
     rec.field_4_value = field_4_value;
     rec.field_5_options = field_5_options;
     rec.field_6_zero = field_6_zero;
     int nTokens = field_8_parsed_expr.Length;
     Ptg[] ptgs = new Ptg[nTokens];
     for (int i = 0; i < nTokens; i++)
     {
         ptgs[i] = field_8_parsed_expr[i].Copy();
     }
     rec.field_8_parsed_expr = ptgs;
     rec.specialCachedValue = specialCachedValue;
     return rec;
 }
 public override void Dispose()
 {
     _formulaRecord = null;
     _sharedValueManager.Dispose();
     _stringRecord = null;
 }
 /// <summary>
 /// Sometimes the shared formula flag "seems" to be erroneously set (because the corresponding
 /// SharedFormulaRecord does not exist). Normally this would leave no way of determining
 /// the Ptg tokens for the formula.  However as it turns out in these
 /// cases, Excel encodes the unshared Ptg tokens in the right place (inside the FormulaRecord). 
 /// So the the only thing that needs to be done is to ignore the erroneous
 /// shared formula flag.
 /// 
 /// This method may also be used for setting breakpoints to help diagnose issues regarding the
 /// abnormally-set 'shared formula' flags.
 /// </summary>
 /// <param name="formula">The formula.</param>
 private static void HandleMissingSharedFormulaRecord(FormulaRecord formula)
 {
     // make sure 'unshared' formula is actually available
     Ptg firstToken = formula.ParsedExpression[0];
     if (firstToken is ExpPtg)
     {
         throw new RecordFormatException(
                 "SharedFormulaRecord not found for FormulaRecord with (isSharedFormula=true)");
     }
     // could log an info message here since this is a fairly unusual occurrence.
     formula.IsSharedFormula = false; // no point leaving the flag erroneously set
 }
Пример #25
0
        public void TestCachedValue_bug46479()
        {
            FormulaRecord fr0 = new FormulaRecord();
            FormulaRecord fr1 = new FormulaRecord();
            // Test some other cached value types 
            fr0.Value = (/*setter*/3.5);
            Assert.AreEqual(3.5, fr0.Value, 0.0);
            fr0.SetCachedResultErrorCode (HSSFErrorConstants.ERROR_REF);
            Assert.AreEqual(HSSFErrorConstants.ERROR_REF, fr0.CachedErrorValue);

            fr0.SetCachedResultBoolean(false);
            fr1.SetCachedResultBoolean(true);
            if (fr0.CachedBooleanValue == true && fr1.CachedBooleanValue == false)
            {
                throw new AssertionException("Identified bug 46479c");
            }
            Assert.AreEqual(false, fr0.CachedBooleanValue);
            Assert.AreEqual(true, fr1.CachedBooleanValue);
        }
Пример #26
0
        public void TestExpFormula()
        {
            byte[] formulaByte = new byte[27];

            formulaByte[4] = (byte)0x0F;
            formulaByte[14] = (byte)0x08;
            formulaByte[18] = (byte)0xE0;
            formulaByte[19] = (byte)0xFD;
            formulaByte[20] = (byte)0x05;
            formulaByte[22] = (byte)0x01;
            FormulaRecord record = new FormulaRecord(TestcaseRecordInputStream.Create(FormulaRecord.sid, formulaByte));
            Assert.AreEqual(0, record.Row, "Row");
            Assert.AreEqual(0, record.Column, "Column");
            byte[] output = record.Serialize();
            Assert.AreEqual(31, output.Length, "Output size"); //includes sid+recordlength
            Assert.AreEqual(1, output[26], "OffSet 22");
        }
Пример #27
0
 private static void verifySharedFormula(FormulaRecord firstFormula, Record rec)
 {
     CellRangeAddress8Bit range = ((SharedValueRecordBase)rec).Range;
     Assert.AreEqual(range.FirstRow, firstFormula.Row);
     Assert.AreEqual(range.FirstColumn, firstFormula.Column);
 }
Пример #28
0
 /**
  * Sometimes the shared formula flag "seems" to be erroneously Set, in which case there is no 
  * call to <c>SharedFormulaRecord.ConvertSharedFormulaRecord</c> and hence the 
  * <c>ParsedExpression</c> field of this <c>FormulaRecord</c> will not Get updated.<br/>
  * As it turns out, this is not a problem, because in these circumstances, the existing value
  * for <c>ParsedExpression</c> is perfectly OK.<p/>
  * 
  * This method may also be used for Setting breakpoints to help diagnose Issues regarding the
  * abnormally-Set 'shared formula' flags. 
  * (see TestValueRecordsAggregate.testSpuriousSharedFormulaFlag()).<p/>
  * 
  * The method currently does nothing but do not delete it without Finding a nice home for this 
  * comment.
  */
 static void HandleMissingSharedFormulaRecord(FormulaRecord formula)
 {
     // could log an info message here since this is a fairly Unusual occurrence.
 }
Пример #29
0
        /** 
         * Creates a non shared formula from the shared formula 
         * counter part
         */
        public void ConvertSharedFormulaRecord(FormulaRecord formula)
        {
            //Sanity Checks
            int formulaRow = formula.Row;
            int formulaColumn = formula.Column;

            if (!IsInRange(formulaRow, formulaColumn))
            {
                throw new InvalidOperationException("Shared Formula Conversion: Coding Error");
            }

            Ptg[] ptgs = ConvertSharedFormulas(field_7_parsed_expr, formulaRow, formulaColumn);
            formula.ParsedExpression = ptgs;
            //Now its not shared!
            formula.IsSharedFormula=false;
        }