Click here to Skip to main content
15,885,985 members
Articles / Programming Languages / C#

Universal Framework for Science and Engineering - Part 2: Regression

Rate me:
Please Sign up or sign in to vote.
4.77/5 (19 votes)
11 Jul 20067 min read 51.1K   5K   76  
An article on universal scalable engineering framework applications.
using System;
using System.Collections.Generic;
using System.Collections;
using System.Text;

using MathGraph;

namespace CategoryTheory
{
    /// <summary>
    /// DiagramLimit
    /// </summary>
    public class CategoryDiagram
    {

        /// <summary>
        /// Out of diagram test
        /// </summary>
        static public readonly string ObjectOutOfDiagram = "Diagram does not contains object";

        /// <summary>
        /// Extra object in diagram text
        /// </summary>
        static public readonly string ExtraArrow = "Extra object";

        /// <summary>
        /// Shortage of in diagram text
        /// </summary>
        static public readonly string ArrowsShortage = "Shortage of arrows in diagram";

        /// <summary>
        /// Graph
        /// </summary>
        private Digraph graph;

        /// <summary>
        /// Arrows hashtable
        /// </summary>
        private Hashtable arrows = new Hashtable();

        /// <summary>
        /// Objects
        /// </summary>
        private ArrayList objects = new ArrayList();

        /// <summary>
        /// Sources
        /// </summary>
        private Hashtable sources = new Hashtable();

        /// <summary>
        /// Targets
        /// </summary>
        private Hashtable targets = new Hashtable();

        /// <summary>
        /// Category
        /// </summary>
        private ICategory category;

        /// <summary>
        /// Limit
        /// </summary>
        private ICategoryObject lim;

        /// <summary>
        /// Limit arrow
        /// </summary>
        private ICategoryArrow limArrow;

        /// <summary>
        /// Limit id arrows
        /// </summary>
        private ArrayList limIdArrows;

        /// <summary>
        /// Limit function arrowa
        /// </summary>
        private ArrayList limFuncArrows;

        /// <summary>
        /// Lim id arrow
        /// </summary>
        private ICategoryArrow limIdArrow;

        /// <summary>
        /// Limit fuctional arrow
        /// </summary>
        private ICategoryArrow limFuncArrow;

        /// <summary>
        /// Limit arrows
        /// </summary>
        private Hashtable limArrows;

        /// <summary>
        /// Colimit
        /// </summary>
        private ICategoryObject colim;

        /// <summary>
        /// Colimit arrow
        /// </summary>
        private ICategoryArrow colimArrow;

        /// <summary>
        /// Colimit id arrows
        /// </summary>
        private ArrayList colimIdArrows;

        /// <summary>
        /// Colimit function arrowa
        /// </summary>
        private ArrayList colimFuncArrows;

        /// <summary>
        /// Colim id arrow
        /// </summary>
        private ICategoryArrow colimIdArrow;

        /// <summary>
        /// Colimit fuctional arrow
        /// </summary>
        private ICategoryArrow colimFuncArrow;

        /// <summary>
        /// Coimit arrows
        /// </summary>
        private Hashtable colimArrows;

        /// <summary>
        /// Constructor
        /// </summary>
        /// <param name="graph">Graph</param>
        /// <param name="category">Category</param>
        public CategoryDiagram(Digraph graph, ICategory category)
        {
            this.graph = graph;
            this.category = category;
            for (int i = 0; i < graph.Count; i++)
            {
                ICategoryObject o = graph[i].Object as ICategoryObject;
                CategoryObjectPair idPair = new CategoryObjectPair(o, o);
                ICategoryArrow id = o.Id;
                arrows[idPair] = id;
                objects.Add(o);
                ArrayList s = new ArrayList();
                s.Add(id);
                sources[o] = s;
                ArrayList t = new ArrayList();
                t.Add(id);
                targets[o] = t;
            }
            for (int i = 0; i < graph.Count; i++)
            {
                DigraphVertex o = graph[i];
                getPaths(o, o);
            }
        }

        /// <summary>
        /// Count of objects
        /// </summary>
        public int Count
        {
            get
            {
                return objects.Count;
            }
        }

        /// <summary>
        /// Digraph
        /// </summary>
        public Digraph Graph
        {
            get
            {
                return graph;
            }
        }

        /// <summary>
        /// Access to i th object
        /// </summary>
        public ICategoryObject this[int i]
        {
            get
            {
                return objects[i] as ICategoryObject;
            }
        }

        /// <summary>
        /// Access to arrow by pair
        /// </summary>
        public ICategoryArrow this[CategoryObjectPair p]
        {
            get
            {
                return arrows[p] as ICategoryArrow;
            }
        }

        /// <summary>
        /// Gets outcoming arrows
        /// </summary>
        /// <param name="o">The soutrce</param>
        /// <returns>List of outcoming arrows</returns>
        public ArrayList GetOutcomingArrows(ICategoryObject o)
        {
            return sources[o] as ArrayList;
        }

        /// <summary>
        /// Gets incoming arrows
        /// </summary>
        /// <param name="o">The target</param>
        /// <returns>List of outcoming arrows</returns>
        public ArrayList GetIncomingArrows(ICategoryObject o)
        {
            return targets[o] as ArrayList;
        }

        /// <summary>
        /// Keys of arrows table
        /// </summary>
        public ICollection Keys
        {
            get
            {
                return arrows.Keys;
            }
        }

        /// <summary>
        /// Gets arrow from limit to diagram object
        /// </summary>
        /// <param name="o">The diagram object</param>
        /// <returns>The arrow</returns>
        public ICategoryArrow GetLimArrow(ICategoryObject o)
        {
            return limArrows[o] as ICategoryArrow;
        }

        /// <summary>
        /// Limit
        /// </summary>
        public ICategoryObject Lim
        {
            get
            {
                if (lim == null)
                {
                    createLim();
                }
                return lim;
            }
        }

        /// <summary>
        /// Gets arrow to lim
        /// </summary>
        /// <param name="arrows">Arrows to objects</param>
        /// <returns>The arrow to lim</returns>
        public ICategoryArrow GetArrowToLim(ArrayList arrows)
        {
            Hashtable arrowsHash = new Hashtable();
            ICategoryObject source = null;
            foreach (ICategoryArrow arrow in arrows)
            {
                if (source == null)
                {
                    source = arrow.Source;
                }
                if (source != arrow.Source)
                {
                    throw new CategoryException(CategoryException.DifferentSources,
                        new ICategoryObject[] { source, arrow.Source });
                }
                if (!objects.Contains(arrow.Target))
                {
                    throw new CategoryException(ObjectOutOfDiagram, arrow.Target);
                }
                if (arrowsHash.ContainsKey(arrow.Target))
                {
                    throw new CategoryException(ExtraArrow, arrow);
                }
                arrowsHash[arrow.Target] = arrow;
            }
            foreach (object o in objects)
            {
                if (!arrowsHash.ContainsKey(o))
                {
                    throw new CategoryException(ArrowsShortage, o);
                }
            }
            foreach (CategoryObjectPair pair in Keys)
            {
                ICategoryArrow ar = this[pair];
                ICategoryArrow first = arrowsHash[pair.Source] as ICategoryArrow;
                ICategoryArrow second = arrowsHash[pair.Target] as ICategoryArrow;
                ICategoryArrow composition = ar.Compose(category, first);
                if (!composition.Equals(second))
                {
                    throw new CategoryException(CategoryException.NonCommutativePath, ar);
                }
            }
            Hashtable sortedTable = new Hashtable();
            foreach (ICategoryArrow ar in arrows)
            {
                int i = objects.IndexOf(ar.Target);
                sortedTable[i] = ar;
            }
            ArrayList sortedArrows = new ArrayList();
            for (int i = 0; i < sortedTable.Count; i++)
            {
                sortedArrows.Add(sortedTable[i]);
            }
            IDirectProductCategory productCategory = category as IDirectProductCategory;
            ICategoryArrow arrowToProduct =
                productCategory.GetArrowToDirectProduct(source, limIdArrow.Source, sortedArrows);
            IEqualizerCategory equalizerCategory = category as IEqualizerCategory;
            ICategoryArrow res = equalizerCategory.GetArrowToEqualizer(limArrow,
                arrowToProduct, limIdArrow, limFuncArrow);
            return res;
        }

        /// <summary>
        /// Gets arrow from limit to diagram object
        /// </summary>
        /// <param name="o">The diagram object</param>
        /// <returns>The arrow</returns>
        public ICategoryArrow GetColimArrow(ICategoryObject o)
        {
            return colimArrows[o] as ICategoryArrow;
        }

        /// <summary>
        /// Limit
        /// </summary>
        public ICategoryObject Colim
        {
            get
            {
                if (colim == null)
                {
                    createColim();
                }
                return colim;
            }
        }

        /// <summary>
        /// Gets arrow from colim
        /// </summary>
        /// <param name="arrows">Arrows from objects</param>
        /// <returns>Arrow from colim</returns>
        public ICategoryArrow GetArrowFromColim(ArrayList arrows)
        {
            Hashtable arrowsHash = new Hashtable();
            ICategoryObject target = null;
            foreach (ICategoryArrow arrow in arrows)
            {
                if (target == null)
                {
                    target = arrow.Target;
                }
                if (target != arrow.Target)
                {
                    throw new CategoryException(CategoryException.DifferentTargets,
                        new ICategoryObject[] { target, arrow.Target });
                }
                if (!objects.Contains(arrow.Source))
                {
                    throw new CategoryException(ObjectOutOfDiagram, arrow.Source);
                }
                if (arrowsHash.ContainsKey(arrow.Source))
                {
                    throw new CategoryException(ExtraArrow, arrow);
                }
                arrowsHash[arrow.Source] = arrow;
            }
            foreach (object o in objects)
            {
                if (!arrowsHash.ContainsKey(o))
                {
                    throw new CategoryException(ArrowsShortage, o);
                }
            }
            foreach (CategoryObjectPair pair in Keys)
            {
                ICategoryArrow ar = this[pair];
                ICategoryArrow first = arrowsHash[pair.Target] as ICategoryArrow;
                ICategoryArrow second = arrowsHash[pair.Source] as ICategoryArrow;
                ICategoryArrow composition = first.Compose(category, ar);
                if (!composition.Equals(second))
                {
                    throw new CategoryException(CategoryException.NonCommutativePath, ar);
                }
            }
            Hashtable sortedTable = new Hashtable();
            foreach (ICategoryArrow ar in arrows)
            {
                int i = objects.IndexOf(ar.Source);
                sortedTable[i] = ar;
            }
            ArrayList sortedArrows = new ArrayList();
            for (int i = 0; i < sortedTable.Count; i++)
            {
                sortedArrows.Add(sortedTable[i]);
            }
            IDirectSumCategory sumCategory = category as IDirectSumCategory;
            ICategoryArrow arrowFromSum =
                sumCategory.GetArrowFromDirectSum(target, colimIdArrow.Target, sortedArrows);
            ICoequalizerCategory coequalizerCategory = category as ICoequalizerCategory;
            ICategoryArrow res = coequalizerCategory.GetArrowFromCoequalizer(colimArrow,
                arrowFromSum, colimIdArrow, colimFuncArrow);
            return res;
        }


        /// <summary>
        /// Creates limit
        /// </summary>
        private void createLim()
        {
            if (!(category is IDirectProductCategory))
            {
                throw new CategoryException(CategoryException.DirectProductNotSupported);
            }
            if (!(category is IEqualizerCategory))
            {
                throw new CategoryException(CategoryException.EqualizerNotSupported);
            }
            IDirectProductCategory productCategory = category as IDirectProductCategory;
            ArrayList firstArrows = new ArrayList();
            ICategoryObject firstProduct = productCategory.GetDirectProduct(objects, firstArrows);
            ArrayList endObjects = new ArrayList();
            foreach (object o in arrows.Keys)
            {
                ICategoryArrow a = arrows[o] as ICategoryArrow;
                endObjects.Add(a.Target);
            }
            ArrayList secondArrows = new ArrayList();
            ICategoryObject secondProduct = productCategory.GetDirectProduct(endObjects, secondArrows);
            limIdArrows = new ArrayList();
            foreach (ICategoryArrow tar in secondArrows)
            {
                ICategoryObject t = tar.Target;
                foreach (ICategoryArrow proj in firstArrows)
                {
                    if (proj.Target == t)
                    {
                        limIdArrows.Add(proj);
                        break;
                    }
                }
            }
            limIdArrow = productCategory.GetArrowToDirectProduct(firstProduct, secondProduct, limIdArrows);
            limFuncArrows = new ArrayList();
            foreach (CategoryObjectPair o in arrows.Keys)
            {
                ICategoryArrow tar = this[o];
                foreach (ICategoryArrow proj in firstArrows)
                {
                    if (proj.Target == tar.Source)
                    {
                        ICategoryArrow ar = tar.Compose(category, proj);
                        limFuncArrows.Add(ar);
                        break;
                    }
                }
            }
            limFuncArrow = productCategory.GetArrowToDirectProduct(firstProduct, secondProduct, limFuncArrows);
            IEqualizerCategory equalizerCategory = category as IEqualizerCategory;
            limArrow = equalizerCategory.GetEqualizer(limIdArrow, limFuncArrow);
            lim = limArrow.Source;
            limArrows = new Hashtable();
            foreach (ICategoryArrow proj in firstArrows)
            {
                ICategoryObject t = proj.Target;
                ICategoryArrow ar = proj.Compose(category, limArrow);
                limArrows[t] = ar;
            }
        }


        /// <summary>
        /// Creates limit
        /// </summary>
        private void createColim()
        {
            if (!(category is IDirectSumCategory))
            {
                throw new CategoryException(CategoryException.DirectSumNotSupported);
            }
            if (!(category is IEqualizerCategory))
            {
                throw new CategoryException(CategoryException.CoequalizerNotSupported);
            }
            IDirectSumCategory sumCategory = category as IDirectSumCategory;
            ArrayList firstArrows = new ArrayList();
            ICategoryObject firstSum = sumCategory.GetDirectSum(objects, firstArrows);
            ArrayList beginObjects = new ArrayList();
            foreach (object o in arrows.Keys)
            {
                ICategoryArrow a = arrows[o] as ICategoryArrow;
                beginObjects.Add(a.Source);
            }
            ArrayList secondArrows = new ArrayList();
            ICategoryObject secondSum = sumCategory.GetDirectSum(beginObjects, secondArrows);
            colimIdArrows = new ArrayList();
            foreach (ICategoryArrow sar in secondArrows)
            {
                ICategoryObject s = sar.Source;
                foreach (ICategoryArrow proj in firstArrows)
                {
                    if (proj.Source == s)
                    {
                        colimIdArrows.Add(proj);
                        break;
                    }
                }
            }
            colimIdArrow = sumCategory.GetArrowFromDirectSum(firstSum, secondSum, colimIdArrows);
            colimFuncArrows = new ArrayList();
            foreach (CategoryObjectPair o in arrows.Keys)
            {
                ICategoryArrow sar = this[o];
                foreach (ICategoryArrow proj in firstArrows)
                {
                    if (proj.Source == sar.Target)
                    {
                        ICategoryArrow ar = proj.Compose(category, sar);
                        colimFuncArrows.Add(ar);
                        break;
                    }
                }
            }
            colimFuncArrow = sumCategory.GetArrowFromDirectSum(firstSum, secondSum, colimFuncArrows);
            ICoequalizerCategory coequalizerCategory = category as ICoequalizerCategory;
            colimArrow = coequalizerCategory.GetCoequalizer(colimIdArrow, colimFuncArrow);
            colim = colimArrow.Target;
            colimArrows = new Hashtable();
            foreach (ICategoryArrow proj in firstArrows)
            {
                ICategoryObject s = proj.Source;
                ICategoryArrow ar = colimArrow.Compose(category, proj);
                colimArrows[s] = ar;
            }
        }


        /// <summary>
        /// Gets paths
        /// </summary>
        /// <param name="v">Root object</param>
        /// <param name="ob">Current object</param>
        private void getPaths(DigraphVertex v, DigraphVertex ob)
        {
            CategoryObjectPair pair = new CategoryObjectPair(v.Object as ICategoryObject,
                ob.Object as ICategoryObject);
            ICategoryArrow theArrow = this[pair];
            foreach (DigraphEdge edge in ob.OutcomingEdges)
            {
                DigraphVertex vo = edge.Target;
                ICategoryArrow ar = edge.Object as ICategoryArrow;
                CategoryObjectPair p = new CategoryObjectPair(v.Object as ICategoryObject, ar.Target);
                ICategoryArrow newArrow = ar.Compose(category, theArrow);
                if (arrows.ContainsKey(p))
                {
                    ICategoryArrow prev = this[p];
                    ICategoryArrow comp = ar.Compose(category, theArrow);
                    if (!prev.Equals(newArrow))
                    {
                        throw new CategoryException(CategoryException.NonCommutativePath);
                    }
                    continue;
                }
                arrows[p] = newArrow;
                ArrayList s = sources[p.Source] as ArrayList;
                s.Add(newArrow);
                ArrayList t = targets[p.Target] as ArrayList;
                t.Add(newArrow);
                getPaths(v, vo);
            }
        }
    }
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here


Written By
Architect
Russian Federation Russian Federation
Ph. D. Petr Ivankov worked as scientific researcher at Russian Mission Control Centre since 1978 up to 2000. Now he is engaged by Aviation training simulators http://dinamika-avia.com/ . His additional interests are:

1) Noncommutative geometry

http://front.math.ucdavis.edu/author/P.Ivankov

2) Literary work (Russian only)

http://zhurnal.lib.ru/editors/3/3d_m/

3) Scientific articles
http://arxiv.org/find/all/1/au:+Ivankov_Petr/0/1/0/all/0/1

Comments and Discussions