using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace lkfxdok.LKF
{
    public class LKFLine
    {
        string _line;
        string[] _elements;
        SortedDictionary<int, string> _replace;
        int _maxIndex;

        string[] _keyParts;
        int _lastKeyPartLength;

        Aufenthalt _aufenthalt;


        internal LKFLine (string line)
        {
            _line = line;
        }

        internal LKFLine(string satzart_or_line, Aufenthalt aufenthalt)
        {
            _aufenthalt = aufenthalt;
            _line = satzart_or_line;
        }

        public string Satzart
        {
            get
            {
                return this[0];
            }
        }

        public string[] GetKeyParts (int keyPartLength)
        {
            if (keyPartLength == _lastKeyPartLength && _keyParts != null)
            {
                return _keyParts;
            }

            _lastKeyPartLength = keyPartLength;
            _keyParts = new string[keyPartLength];

            if (_replace == null)
            {
                if (_elements != null && _elements.Length >= keyPartLength) {
                    Array.Copy(_elements, _keyParts, keyPartLength);
                }
            }
            else
            {
                for (int i = 0; i < keyPartLength; i++)
                {
                    string v;
                    if (_replace.TryGetValue(i, out v))
                        _keyParts[i] = v;
                    else if (_elements != null && _elements.Length > i)
                        _keyParts[i] = _elements[i];
                    else
                        _keyParts[i] = null;
                }
            }
            return _keyParts;
        }
            

        public string this[int index]
        {
            get
            {
                string res;
                if (_replace != null && _replace.TryGetValue(index, out res))
                    return res;
                if (_elements == null)
                    _elements = _line.Split('|');
                if (_elements.Length > index && index >= 0)
                    return _elements[index];
                return string.Empty;
            }
            internal set
            {
                if (_replace == null)
                    _replace = new SortedDictionary<int, string>();
                _replace[index] = value;
                if (index > _maxIndex) _maxIndex = index;
                if (_aufenthalt != null) _aufenthalt.Synchronized = false;
            }
        }

        public int GetInt (int index)
        {
            var v = this[index];
            if (!string.IsNullOrEmpty(v))
            {
                try
                {
                    return Convert.ToInt32(v);
                }
                catch
                {
                    return 0;
                }
            }
            return 0;
            
            /*

            try
            {
            }
            catch
            {
                return 0;
            }
            */
        } 

        public string OriginalLine
        {
            get
            {
                return _line;
            }
        }

        internal bool Modified
        {
            get
            {
                return _replace != null;
            }
        }

        internal Aufenthalt Aufenthalt
        {
            get
            {
                return _aufenthalt;
            }
        }

        public string Line
        {
            get
            {
                return GetLine(null, false);
            }
        }

        internal string[] Elements
        {
            get
            {
                return _elements;
            }
        }

        public int ElementCount
        {
            get
            {
                return _elements != null ? _elements.Length : 0;
            }
        }

        internal string GetLine (string[] replacements, bool apply)
        {

            if (_elements == null)
                _elements = _line.Split('|');

            int replacementsLength = replacements != null ? replacements.Length : 0;
            int maxIndex = replacementsLength;
            if (_elements.Length > maxIndex)
                maxIndex = _elements.Length;

            if (maxIndex < _maxIndex)
                maxIndex = _maxIndex;

            string[] lineParts = new string[maxIndex + 1];

            if (replacements != null)
                replacements.CopyTo(lineParts, 0);
            lineParts[0] = _elements[0];
            for (int i = replacementsLength; i < _elements.Length; i++)
            {
                lineParts[i] = _elements[i];
            }

            if (_replace != null)
            {
                foreach (var pair in _replace)
                    lineParts[pair.Key] = pair.Value;
            }

            if (apply)
            {
                _elements = lineParts;
                _replace = null;
            }

            return string.Join("|", lineParts);
        }
    }
}
