Ejemplo n.º 1
0
        /// <summary>Add some data to the heap.</summary>
        internal virtual int PutData(Object data)
        {
            int size = ArrayFuncs.ComputeSize(data);

            ExpandHeap(size);
            MemoryStream bo = new MemoryStream(size);

            try
            {
                BufferedDataStream o = new BufferedDataStream(bo);
                o.WriteArray(data);
                o.Flush();
                o.Close();
            }
            catch (IOException)
            {
                throw new FitsException("Unable to write variable column length data");
            }

            Array.Copy(bo.ToArray(), 0, heap, heapSize, size);
            int oldOffset = heapSize;

            heapSize += size;

            // change suggested in .99.1 version:
            heapOffset = heapSize;

            return(oldOffset);
        }
        protected static int[] ComputeByteWidths(Array[] a)
        {
            int[] result = new int[a.Length];

            for (int i = 0; i < a.Length; ++i)
            {
                result[i] = ArrayFuncs.ComputeSize(a[i]);
            }

            return(result);
        }
        protected void SetupRenderers()
        {
            Array[] modelRow  = ReplaceTroolean(_rs.ModelRow);
            Array[] modelRow2 = null;
            switch (_writeMode)
            {
            case StringWriteMode.HEAP:
            case StringWriteMode.PAD:
                modelRow2 = CopyModelRowReplaceStrings(modelRow, new int[2]);
                modelRow2 = CopyModelRowStripUnknowns(modelRow2, new byte[1]);
//          _rowSizeInBytes = ArrayFuncs.ComputeSize(CopyModelRowReplaceStrings(modelRow, new int[2]));
                _rowSizeInBytes = ArrayFuncs.ComputeSize(modelRow2);
                modelRow2       = CopyModelRowStripUnknowns(modelRow, new byte[1]);
                //myHeader = ManufactureHeader(modelRow, _rs.ColumnNames, _rs.TNULL, _rs.NRows);
                myHeader             = ManufactureHeader(modelRow2, _rs.ColumnNames, _rs.TNULL, _rs.NRows);
                _stringArrayRenderer = ByteRenderer.STRING_ARRAY_RENDERER_HEAP;
                break;

            case StringWriteMode.TRUNCATE:
                modelRow2            = CopyModelRowReplaceStrings(modelRow, new String[] { new String(' ', _stringTruncationLength) });
                modelRow2            = CopyModelRowStripUnknowns(modelRow2, new byte[1]);
                _rowSizeInBytes      = ArrayFuncs.ComputeSize(modelRow2);
                myHeader             = ManufactureHeader(modelRow2, _rs.ColumnNames, _rs.TNULL, _rs.NRows);
                _stringArrayRenderer =
                    new ByteRenderer.StringArrayByteRendererTruncate(_stringTruncationLength, _padChar, _padLeft, false);
                break;
            }

            _hasStrings = false;
            for (int i = 0; i < _rs.ModelRow.Length; ++i)
            {
                _byteRenderers[i] = ByteRenderer.GetByteRenderer(_rs.ModelRow[i].GetType());

                if (_rs.ModelRow[i] is String[])
                {
                    _byteRenderers[i] = _stringArrayRenderer;
                    _hasStrings       = true;
                }

                if (_byteRenderers[i].GetType() == typeof(ByteRenderer.NullByteRenderer))
                {
                    myHeader.AddComment("COLUMN " + (i + 1) + " NULL DUE TO UNKNOWN TYPE.");
                }
            }
        }
        protected static int[] GetStringIndices(Array[] a)
        {
            int[] result = new int[a.Length];
            for (int i = 0, offset = 0; i < a.Length; ++i)
            {
                result[i] = -1;
                if (a[i] is String[])
                {
                    result[i] = offset;
                    offset   += 8; // two ints, position & length
                }
                else if (a[i] is Troolean[])
                {
                    offset += 1; // one char, 'T', 'F', or null
                }
                else
                {
                    offset += ArrayFuncs.ComputeSize(a[i]);
                }
            }

            return(result);
        }
Ejemplo n.º 5
0
 /// <summary>Create an ImageData object using the specified object to
 /// initialize the data array.
 /// </summary>
 /// <param name="x">The initial data array.  This should be a primitive
 /// array but this is not checked currently.
 /// </param>
 public ImageData(Object x)
 {
     dataArray = x;
     byteSize  = ArrayFuncs.ComputeSize(x);
 }
        /// <summary>
        ///   Writes this binary table with data first going
        ///   to a temp file (and heap file if necessary),
        ///   then with header going to destination stream,
        ///   then merging heap with table data if necessary
        ///   and copying these to destination stream.
        /// </summary>
        /// <param name="s">The destination stream.</param>
        /// steps:
        /// 1) write the table to a tempfile
        ///    byterenderers write data to the heap if necessary
        ///    byterenderers return heap positions and lengths if necessary
        ///    these are returned as a byte sequence like any other data
        ///    and are written to the table like any other data
        /// 2) fix the header
        ///    write the header to the main stream
        /// 3) write the table tempfile to the main stream, merging heap if necessary
        /// what a pain
        protected void WritePadOutput(ArrayDataIO s)
        {
            String tempFilename = CreateTempFilename() + "temp.tmp";
            String heapFilename = CreateTempFilename() + "heap.tmp";
            Stream tempS        = new ActualBufferedStream(new FileStream(tempFilename, FileMode.Create));
            Stream heapS        = null;

            //Stream tempS = new BufferedStream(new FileStream(tempFilename, FileMode.Create), 4096);
            int[] maxColWidths  = null;
            int[] stringIndices = GetStringIndices(_rs.ModelRow);
            int[] byteWidths    = ComputeByteWidths(CopyModelRowStripUnknowns(ReplaceTroolean(_rs.ModelRow), new byte[1]));
            int   nRows         = 0;
            int   maxColWidth   = 0;

            if (_hasStrings)
            {
                maxColWidths = new int[_byteRenderers.Length];
                heapS        = new HeapStream(new FileStream(heapFilename, FileMode.Create));
                //heapS = new BufferedStream(new FileStream(heapFilename, FileMode.Create));
                for (int col = 0; col < _byteRenderers.Length; ++col)
                {
                    _byteRenderers[col].Heap = heapS;
                    maxColWidths[col]        = -1;
                }
            }

            #region 1) write the table
            for (Array[] els = _rs.GetNextRow(ref _row); els != null;)
            {
                ++nRows;
                for (int col = 0; col < _byteRenderers.Length; ++col)
                {
                    _byteRenderers[col].Write(els[col], tempS);
                    if (els[col] is String[] && maxColWidths[col] < ((String[])els[col])[0].Length)
                    {
                        maxColWidths[col] = ((String[])els[col])[0].Length;

                        if (maxColWidth < maxColWidths[col])
                        {
                            maxColWidth = maxColWidths[col];
                        }
                    }
                }

                els = _rs.GetNextRow(ref _row);
            }
            tempS.Flush();
            heapS.Flush();
            #endregion

            #region 2) fix the header and write it to the main stream
            if (_hasStrings)
            {
                // fix NAXIS1, NAXIS2
                Array[] modelRow2 = CopyModelRowReplaceStrings(ReplaceTroolean(_rs.ModelRow), null);
                //modelRow2 = CopyModelRowStripUnknowns(modelRow2, new byte[1]);
                for (int i = 0; i < modelRow2.Length; ++i)
                {
                    if (modelRow2[i] == null)
                    {
                        modelRow2[i] = new String[] { new String(' ', maxColWidths[i]) };
                        myHeader.RemoveCard("TFORM" + (i + 1));
                        myHeader.InsertValue("TFORM" + (i + 1), maxColWidths[i] + "A", null, "TDIM" + (i + 1));
                    }
                }
                modelRow2 = CopyModelRowStripUnknowns(modelRow2, new byte[1]);
                myHeader.RemoveCard("NAXIS1");
                myHeader.InsertValue("NAXIS1", ArrayFuncs.ComputeSize(modelRow2), "row width in bytes", "NAXIS2");
                myHeader.RemoveCard("NAXIS2");
                myHeader.InsertValue("NAXIS2", nRows, "number of rows", "PCOUNT");
                myHeader.RemoveCard("THEAP");
            }
            myHeader.Write(s);
            #endregion

            #region 3) write the table tempfile to the main stream
            tempS.Seek(0, SeekOrigin.Begin);
            heapS.Seek(0, SeekOrigin.Begin);
            // man, if you can't even fit a row into memory, I give up
            byte[] row    = new byte[_rowSizeInBytes]; // this is the old size
            byte[] padBuf = SupportClass.ToByteArray(new String(_padChar, maxColWidth));
            int    len    = 0;
            int    off    = 0;
            for (int nRead = tempS.Read(row, 0, row.Length), rowOffset = 0; nRead > 0; rowOffset = 0)
            {
                for (int i = 0; i < byteWidths.Length; ++i)
                {
                    if (stringIndices[i] != -1)
                    {
                        Array.Reverse(row, stringIndices[i], 4);     // fix the length bytes
                        Array.Reverse(row, stringIndices[i] + 4, 4); // fix the pos bytes
                        len = BitConverter.ToInt32(row, stringIndices[i]);
                        off = BitConverter.ToInt32(row, stringIndices[i] + 4);
                        if (_padLeft)
                        {
                            s.Write(padBuf, 0, maxColWidths[i] - len);
                            heapS.Seek(off, SeekOrigin.Begin);
                            int bufread = heapS.Read(_buf, 0, len);
                            s.Write(_buf, 0, len);
                        }
                        else
                        {
                            heapS.Seek(off, SeekOrigin.Begin);
                            heapS.Read(_buf, 0, len);
                            s.Write(_buf, 0, len);
                            s.Write(padBuf, 0, maxColWidths[i] - len);
                        }
                        rowOffset += 8; // advance 2 ints into the row
                    }
                    else
                    {
                        // s better be buffered, or this is going to be slow.  But since s is ArrayDataIO,
                        // and the only current concrete ArrayDataIO implementations are buffered,
                        // I think we're good.
                        // **** MAKE SURE BUFFEREDSTREAM USED BY BUFFEREDDATASTREAM IS GOOD *****
                        s.Write(row, rowOffset, byteWidths[i]);
                        rowOffset += byteWidths[i];
                    }
                }
                nRead = tempS.Read(row, 0, row.Length);
            }
            tempS.Close();
            heapS.Close();
            File.Delete(tempFilename);
            File.Delete(heapFilename);

            // pad the table
            int tableWidth = 0;
            for (int i = 0; i < byteWidths.Length; ++i)
            {
                if (stringIndices[i] != -1)
                {
                    tableWidth += maxColWidths[i];
                }
                else
                {
                    tableWidth += byteWidths[i];
                }
            }
            int pad = FitsUtil.Padding((long)nRows * (long)tableWidth);
            s.Write(new byte[pad], 0, pad);
            #endregion
        }
Ejemplo n.º 7
0
        public void TestRandomGroup()
        {
            //float[,] fa = new float[20,20];
            float[][] fa = new float[20][];
            for (int i = 0; i < fa.Length; i++)
            {
                fa[i] = new float[20];
            }
            float[] pa = new float[3];

            BufferedFile bf = new BufferedFile(
                TestFileSetup.GetTargetFilename("rg1.fits"),
                FileAccess.ReadWrite,
                FileShare.ReadWrite);

            Object[][] data = new Object[1][];
            data[0]    = new Object[2];
            data[0][0] = pa;
            data[0][1] = fa;

            Console.Out.WriteLine("***** Write header ******");
            BasicHDU hdu = Fits.MakeHDU(data);
            Header   hdr = hdu.Header;

            // Change the number of groups
            hdr.AddValue("GCOUNT", 20, "Number of groups");
            hdr.Write(bf);

            Console.Out.WriteLine("***** Write data group by group ******");
            for (int i = 0; i < 20; i += 1)
            {
                for (int j = 0; j < pa.Length; j += 1)
                {
                    pa[j] = i + j;
                }
                for (int j = 0; j < fa.GetLength(0); j += 1)
                {
                    try
                    {
                        //  fa[j, j] = i * j;
                        fa[j][j] = i * j;
                    }
                    catch (Exception e)
                    {
                        Console.WriteLine(e.Message);
                        Console.WriteLine("i ,j value:" + i + "   " + j);
                    }
                }
                // Write a group
                bf.WriteArray(data);
            }

            byte[] padding = new byte[FitsUtil.Padding(20 * ArrayFuncs.ComputeSize(data))];
            Console.Out.WriteLine("****** Write padding ******");
            bf.Write(padding);

            bf.Flush();
            bf.Close();
            bf.Dispose();

            Fits f = null;

            try
            {
                Console.Out.WriteLine("****** Read data back in ******");
                f = new Fits(TestFileSetup.GetTargetFilename("rg1.fits"));
                BasicHDU[] hdus = f.Read();

                data = (Object[][])hdus[0].Kernel;
                // data = hdus[0].Kernel;
                Console.Out.WriteLine("**** Check parameter and data info *****");
                for (int i = 0; i < data.Length; i += 1)
                {
                    pa = (float[])data[i][0];
                    // fa = (float[,]) data[i,1];
                    Array[] tfa = (Array[])data[i][1];
                    for (int j = 0; j < pa.Length; j += 1)
                    {
                        Assert.AreEqual((float)(i + j), pa[j]);
                    }
                    for (int j = 0; j < fa.Length; j += 1)
                    {
                        // Assert.AreEqual("dataTest:" + i + " " + j, (float)(i * j), fa[j,j]);
                        Assert.AreEqual((float)(i * j), ((Array)tfa.GetValue(j)).GetValue(j));
                    }
                }

                f.Close();

                Console.Out.WriteLine("**** Create HDU from kernel *****");
                f = new Fits();

                // Generate a FITS HDU from the kernel.
                f.AddHDU(Fits.MakeHDU(data));
                bf = new BufferedFile(
                    TestFileSetup.GetTargetFilename("rg2.fits"),
                    FileAccess.ReadWrite,
                    FileShare.ReadWrite);

                Console.Out.WriteLine("**** Write new file *****");
                f.Write(bf);
                bf.Flush();
                bf.Close();
                bf.Dispose();
                f.Close();

                Console.Out.WriteLine("**** Read and check *****");
                f    = new Fits(TestFileSetup.GetTargetFilename("rg2.fits"));
                data = (Object[][])f.Read()[0].Kernel;

                for (int i = 0; i < data.Length; i += 1)
                {
                    pa = (float[])data[i][0];
                    //   fa = (float[,]) data[i,1];
                    Array[] tfa = (Array[])data[i][1];

                    for (int j = 0; j < pa.Length; j += 1)
                    {
                        Assert.AreEqual((float)(i + j), pa[j]);
                    }

                    for (int j = 0; j < fa.Length; j += 1)
                    {
                        //Assert.AreEqual("dataTest:" + i + " " + j, (float)(i * j), fa[j,j]);
                        Assert.AreEqual((float)(i * j), ((Array)tfa.GetValue(j)).GetValue(j));
                    }
                }
            }
            finally
            {
                if (f != null)
                {
                    f.Close();
                }
            }
        }
Ejemplo n.º 8
0
 /// <summary>Create an UndefinedData object using the specified object.</summary>
 public UndefinedData(Object x)
 {
     byteSize = ArrayFuncs.ComputeSize(x);
     data     = new byte[(int)byteSize];
 }