예제 #1
0
        /// <summary>
        /// method to write data
        /// </summary>
        /// <param name="o"></param>
        public override void Write(ArrayDataIO o)
        {
            // Don't need to write null data (noted by Jens Knudstrup)
            if (byteSize == 0)
            {
                return ;
            }

            // changes suggested in .97 version:
            if (dataArray == null)
            {
                if (tiler != null)
                {
                    // Need to read in the whole image first.
                    try
                    {
                        dataArray = tiler.CompleteImage;
                    }
                    catch(IOException)
                    {
                        throw new FitsException("Error attempting to fill image");
                    }
                }
                else if (dataArray == null && dataDescription != null)
                {
                    // Need to create an array to match a specified header.
                    dataArray = ArrayFuncs.NewInstance(dataDescription.type, dataDescription.dims);
                }
                else
                {
                    // This image isn't ready to be written!
                    throw new FitsException("Null image data");
                }
            }

            try
            {
                o.WriteArray(dataArray);
            }
            catch(IOException e)
            {
                throw new FitsException("IO Error on image write: " + e);
            }

            byte[] padding = new byte[FitsUtil.Padding(TrueSize)];
            try
            {
                o.Write(padding);
                o.Flush();
            }
            catch(IOException e)
            {
                throw new FitsException("Error writing padding: " + e);
            }
        }
예제 #2
0
파일: Header.cs 프로젝트: rwg0/csharpfits
        /// <summary>Write the current header (including any needed padding) to the
        /// output stream.</summary>
        /// <param name="dos">The output stream to which the data is to be written.</param>
        /// <exception cref="FitsException">FitsException if the header could not be written.</exception>
        public void Write(ArrayDataIO dos)
        {
            fileOffset = FitsUtil.FindOffset(dos);

            // change suggested in .99.1 version: used HeaderOrder to sort keyword before write op.
            // Ensure that all cards are in the proper order.
            cards.Sort(new HeaderOrder());

            CheckBeginning();
            CheckEnd();

            if(cards.Count <= 0)
            {
                return ;
            }

            //Cursor cursor = cards.GetCursor(0);
            Cursor cursor = cards.GetCursor();

            try
            {
                while(cursor.MoveNext())
                {
                    HeaderCard card = (HeaderCard)((DictionaryEntry)cursor.Current).Value;
                    byte[] b = SupportClass.ToByteArray(card.ToString());
                    dos.Write(b);
                }

                byte[] padding = new byte[FitsUtil.Padding(NumberOfCards * 80)];
                for (int i = 0; i < padding.Length; i += 1)
                {
                    padding[i] = (byte)' ';// SupportClass.Identity(' ');
                }
                dos.Write(padding);
            }
            catch(IOException e)
            {
                throw new FitsException("IO Error writing header: " + e);
            }
            try
            {
                dos.Flush();
            }
            catch(IOException)
            {
            }
        }
예제 #3
0
 /// <summary>Write the RandomGroupsData.</summary>
 public override void Write(ArrayDataIO str)
 {
     try
     {
         str.WriteArray(dataArray);
         byte[] padding = new byte[FitsUtil.Padding(TrueSize)];
         str.Write(padding);
         str.Flush();
     }
     catch(IOException e)
     {
         throw new FitsException("IO error writing random groups data " + e);
     }
 }
예제 #4
0
        /// <summary>
        ///   Writes this binary table with heap temp file if necessary,
        ///   then fixing nRows and PCOUNT in header,
        ///   then if necessary copying heap file to destination stream.
        /// </summary>
        /// <param name="s">The destination stream.</param>
        /// steps:
        /// 1) write the header to the main stream
        ///    write the table to the main stream
        ///    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
        /// 3) write the heap tempfile to the main stream
        /// what a pain
        protected void WriteHeapOutputWithTempHeapFile(ArrayDataIO s)
        {
            String heapFilename = CreateTempFilename() + "heap.tmp";
              HeapStream heapS = null;
              int[] maxColWidths = null;

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

              #region 1) write the header and the table
              // prep header to make sure it will line up properly with the table later on.
              // since we made the header, we know that anything we add later
              // (except THEAP, accounted for here) will already have been there,
              // so we're not inflating the header
              myHeader.RemoveCard("THEAP");
              if(_hasStrings && _writeMode == StringWriteMode.HEAP)
              {
            myHeader.AddValue("THEAP", 0, null);
              }
              long headerMark = s.Position;
              myHeader.Write(s);

              int nRows = 0;
              for(Array[] els = _rs.GetNextRow(ref _row); els != null;)
              {
            ++nRows;
            for(int col = 0; col < _byteRenderers.Length; ++col)
            {
              _byteRenderers[col].Write(els[col], s);
              if(els[col] is String[])
              {
                maxColWidths[col] = maxColWidths[col] < ((String[])els[col])[0].Length ?
                  ((String[])els[col])[0].Length : maxColWidths[col];
              }
            }

            els = _rs.GetNextRow(ref _row);
              }

              // pad the table.  if there's a heap, pad the heap instead
              if(!_hasStrings)
              {
            int pad = FitsUtil.Padding((long)nRows * (long)_rowSizeInBytes);
            s.Write(new byte[pad], 0, pad);
              }
              s.Flush();
              #endregion

              #region 2) fix the header and write it to the main stream
              myHeader.RemoveCard("NAXIS2");
              myHeader.SetNaxis(2, nRows);
              // shoehorn correct heap information into header
              // PCOUNT, THEAP, and TFORMn
              // fix NAXIS1
              if(_hasStrings)
              {
            long theap = (long)nRows * (long)_rowSizeInBytes;
            int pad = FitsUtil.Padding(theap + heapS.Position);
            int pcount = (int)heapS.Position + pad;
            // here we correct for swapping out actual strings with heap indices/lengths
            myHeader.RemoveCard("NAXIS1");
            myHeader.InsertCard(new HeaderCard("NAXIS1", _rowSizeInBytes, null), "NAXIS2");
            myHeader.RemoveCard("PCOUNT");
            myHeader.InsertCard(new HeaderCard("PCOUNT", pcount, "Length of heap area in bytes"),
              "GCOUNT");
            myHeader.RemoveCard("THEAP");
            // can't fit a long in here!
            if(pcount > 0 && _writeMode == StringWriteMode.HEAP)
            {
              myHeader.AddValue("THEAP", (int)theap, "Position of heap wrt start of binary table");
            }

            // fix the TFORMn entries for string columns
            IEnumerator ie = null;
            bool found = false;
            for(int i = 0; i < maxColWidths.Length; ++i, found = false)
            {
              if(maxColWidths[i] > -1)
              {
                ie = myHeader.GetEnumerator();
                ie.MoveNext();
                for(int j = 0; !found && ie.Current != null; ++j, ie.MoveNext())
                {
                  if(("TFORM" + (i + 1)).Equals(((DictionaryEntry)ie.Current).Key))
                  {
                    myHeader.RemoveCard(j);
                    myHeader.
                      InsertCard(new HeaderCard("TFORM" + (i + 1),
                      "1PA(" + maxColWidths[i] + ")",
                      null), j);
                    found = true;
                  }
                }
              }
            }
              }
              // rewrite the header
              long heapMark = s.Position;
              s.Seek(headerMark, SeekOrigin.Begin);
              myHeader.Write(s);
              #endregion

              #region 3) write the heap tempfile to the main stream
              if(_hasStrings)
              {
            // calculate the pad
            int pad = FitsUtil.Padding((long)nRows * (long)_rowSizeInBytes + heapS.Position);

            s.Seek(heapMark, SeekOrigin.Begin);

            // write heap to the main stream
            heapS.Seek(0, SeekOrigin.Begin);
            for(int nRead = heapS.Read(_buf, 0, _buf.Length); nRead > 0;)
            {
              s.Write(_buf, 0, nRead);
              nRead = heapS.Read(_buf, 0, _buf.Length);
            }
            heapS.Close();
            File.Delete(heapFilename);

            // pad the file
            s.Write(new byte[pad], 0, pad);
              }
              #endregion
        }
예제 #5
0
 public override void Write(ArrayDataIO s)
 {
     System.Threading.Monitor.Enter(this);
       //((Writer)_writerMap[new Config(_rs.NRows != RowSource.NA, _hasStrings, s.CanSeek, _writeMode)]).Write(s);
       Config c = new Config(_rs.NRows != RowSource.NA, _hasStrings, s.CanSeek, _writeMode);
       ((Writer)_writerMap[c]).Write(s);
       s.Flush();
       System.Threading.Monitor.Exit(this);
 }
예제 #6
0
        /// <summary>Write the data to an output stream.</summary>
        public override void Write(ArrayDataIO str)
        {
            // If buffer is still around we can just reuse it,
            // since nothing we've done has invalidated it.
            if (buffer == null)
            {
                if (data == null)
                {
                    throw new FitsException("Attempt to write undefined ASCII Table");
                }

                buffer = new byte[nRows * rowLen];
                bp = new ByteParser(buffer);
                for(int i = 0; i < buffer.Length; i += 1)
                {
                    buffer[i] = (byte)' ';//SupportClass.Identity(' ');
                }

                ByteFormatter bf = new ByteFormatter();
                bf.TruncationThrow = false;
                bf.TruncateOnOverflow = true;

                for (int i = 0; i < nRows; i += 1)
                {
                    for (int j = 0; j < nFields; j += 1)
                    {
                        int offset = i * rowLen + offsets[j];
                        int len = lengths[j];

                        try
                        {
                            if (isNull_Renamed_Field != null && isNull_Renamed_Field[i * nFields + j])
                            {
                                if (nulls[j] == null)
                                {
                                    throw new FitsException("No null value set when needed");
                                }
                                bf.format(nulls[j], buffer, offset, len);
                            }
                            else
                            {
                                if (types[j] == typeof(String))
                                {
                                    String[] s = (String[]) data[j];
                                    bf.format(s[i], buffer, offset, len);
                                }
                                else if (types[j] == typeof(int))
                                {
                                    int[] ia = (int[]) data[j];
                                    bf.format(ia[i], buffer, offset, len);
                                }
                                else if (types[j] == typeof(float))
                                {
                                    float[] fa = (float[]) data[j];
                                    bf.format(fa[i], buffer, offset, len);
                                }
                                else if (types[j] == typeof(double))
                                {
                                    double[] da = (double[]) data[j];
                                    bf.format(da[i], buffer, offset, len);
                                }
                                else if (types[j] == typeof(long))
                                {
                                    long[] la = (long[]) data[j];
                                    bf.format(la[i], buffer, offset, len);
                                }
                            }
                        }
                        catch(TruncationException)
                        {
                            Console.Error.WriteLine("Ignoring truncation error:" + i + "," + j);
                        }
                    }
                }
            }

            // Now write the buffer.
            try
            {
                str.Write(buffer);
                byte[] padding = new byte[FitsUtil.Padding(buffer.Length)];
                for (int i = 0; i < padding.Length; i += 1)
                {
                    padding[i] = (byte) SupportClass.Identity(' ');
                }
                if (buffer.Length > 0)
                {
                    str.Write(padding);
                }
                str.Flush();
            }
            catch(IOException)
            {
                throw new FitsException("Error writing ASCII Table data");
            }
        }
예제 #7
0
 /// <summary>Write out the HDU.</summary>
 public virtual void Write(ArrayDataIO stream)
 {
     if (myHeader != null)
     {
         myHeader.Write(stream);
     }
     if (myData != null)
     {
         myData.Write(stream);
     }
     try
     {
         stream.Flush();
     }
     catch(IOException e)
     {
         throw new FitsException("Error flushing at end of HDU: " + e.Message);
     }
 }