/// <summary>
        /// Inserts the given pseudoObject into the database and returns the newly created one (With the real id and so on)
        /// </summary>
        /// <param name="pseudoValue">The pseudoObject that should be inserted</param>
        /// <param name="doConvert">Function to convert a pseudoObject into a real one with the id given</param>
        /// <param name="doEncode">Encoder to generated the line for the database</param>
        /// <param name="indicator">The indicator of that object</param>
        /// <param name="doParse">LineParser for the object</param>
        /// <param name="getId">Function to get the id (Unique) of an object</param>
        /// <exception cref="DatabaseException">If anything went wrong with the insert</exception>
        /// <returns>The real object (Made from the pseudo and id)</returns>
        private T InsertNewIntoDatabase <T>(T pseudoValue, Func <int, T, T> doConvert, Func <T, int> getId, ObjectEncoder <T> doEncode, LineParser <T> doParse, char indicator)
        {
            // Gets the next id for the object
            int id = this.GetNextIDFor(doParse, getId, indicator);

            // Converts the pseudoObject into a real one
            T realObject = doConvert(id, pseudoValue);

            try
            {
                // Inserts the new object into the database
                using (StreamWriter sr = new StreamWriter(this.FilePath, true, Encoding.UTF8))
                    sr.WriteLine(indicator + doEncode(realObject));

                // Returns the newly inserted object
                return(realObject);
            }
            catch
            {
                throw new DatabaseException("Fehler beim sichern des Wertes in der Datanbank (" + indicator + ").");
            }
        }
        public void WriteObject(ObjectEncoder encoder, Object obj)
        {
            if (_firstObject)
            {
                WriteInt(BinaryObjectEncoder.OBJECT_MAGIC);
                WriteInt(BinaryObjectEncoder.ENCODING_VERSION);
                _firstObject = false;
            }

            MemoryStream objectBuffer = new MemoryStream();
            _outputBufferStack.Add(objectBuffer);

            if (obj == null)
            {
                WriteByte(BinaryObjectEncoder.OBJECT_TYPE_NULL);
            }
            else
            {
                Type clazz = obj.GetType();
                WriteClass(clazz);
                ObjectSerializationHandler handler =
                    ObjectSerializerRegistry.GetHandlerByObjectType(clazz);
                if (handler == null)
                {
                    //we may have special handlers for certain types of arrays
                    //if handler is null, treat like any other array
                    if (obj is Array)
                    {
                        Array array = (Array)obj;
                        int length = array.Length;
                        for (int i = 0; i < length; i++)
                        {
                            Object val = array.GetValue(i);
                            StartAnonymousField();
                            WriteObject(encoder, val);
                            EndField();
                        }
                    }
                    else
                    {
                        throw new ConnectorException("No serializer for class: " + clazz);
                    }
                }
                else
                {
                    handler.Serialize(obj, encoder);
                }
            }

            //write end-object into the current obj buffer
            WriteByte(BinaryObjectEncoder.FIELD_TYPE_END_OBJECT);

            //pop the stack
            _outputBufferStack.RemoveAt(_outputBufferStack.Count - 1);

            //it's a top-level object, flush the constant pool
            if (_outputBufferStack.Count == 0)
            {
                WriteInt(_constantBuffer.Count);
                foreach (String constant in _constantBuffer)
                {
                    WriteString(constant, false);
                    WriteInt(_constantPool[constant]);
                }
                _constantBuffer.Clear();
            }

            //now write the actual object
            objectBuffer.Close();
            byte[] bytes = objectBuffer.ToArray();
            WriteBytes(bytes);
        }
        public void WriteObject(ObjectEncoder encoder, Object obj)
        {
            if (_firstObject)
            {
                WriteInt(BinaryObjectEncoder.OBJECT_MAGIC);
                WriteInt(BinaryObjectEncoder.ENCODING_VERSION);
                _firstObject = false;
            }

            MemoryStream objectBuffer = new MemoryStream();

            _outputBufferStack.Add(objectBuffer);

            if (obj == null)
            {
                WriteByte(BinaryObjectEncoder.OBJECT_TYPE_NULL);
            }
            else
            {
                Type clazz = obj.GetType();
                WriteClass(clazz);
                ObjectSerializationHandler handler =
                    ObjectSerializerRegistry.GetHandlerByObjectType(clazz);
                if (handler == null)
                {
                    //we may have special handlers for certain types of arrays
                    //if handler is null, treat like any other array
                    if (obj is Array)
                    {
                        Array array  = (Array)obj;
                        int   length = array.Length;
                        for (int i = 0; i < length; i++)
                        {
                            Object val = array.GetValue(i);
                            StartAnonymousField();
                            WriteObject(encoder, val);
                            EndField();
                        }
                    }
                    else
                    {
                        throw new ConnectorException("No serializer for class: " + clazz);
                    }
                }
                else
                {
                    handler.Serialize(obj, encoder);
                }
            }

            //write end-object into the current obj buffer
            WriteByte(BinaryObjectEncoder.FIELD_TYPE_END_OBJECT);

            //pop the stack
            _outputBufferStack.RemoveAt(_outputBufferStack.Count - 1);

            //it's a top-level object, flush the constant pool
            if (_outputBufferStack.Count == 0)
            {
                WriteInt(_constantBuffer.Count);
                foreach (String constant in _constantBuffer)
                {
                    WriteString(constant, false);
                    WriteInt(_constantPool[constant]);
                }
                _constantBuffer.Clear();
            }

            //now write the actual object
            objectBuffer.Close();
            byte[] bytes = objectBuffer.ToArray();
            WriteBytes(bytes);
        }