Click here to Skip to main content
65,938 articles
CodeProject is changing. Read more.
Articles
(untagged)

Read CSV input from a text file and add integer values in each string read

0.00/5 (No votes)
16 Oct 2013 1  
Read CSV input from a text file, and add integer values in each string read (line by line). Incorporate Unit Tests to test the program's functionality using C#.

Introduction

Read CSV Input from a text file, and add the integer values in each string read (Line by Line). Incorporate Unit Tests to test the program's functionality.

Background

I have been moving my development language of choice from VB.NET to C# .NET, and one of my most recent tasks has been to code a solution that reads line input from a CSV file with expected delimiters ";" and "," for each line. In my first attempt I got a very long solution, which was rough with errors upon trying to run the code. In the second attempt I shortened the code and made some good discoveries about the power of .NET and C#. So if you are having second thoughts about moving from VB.NET to C# I guess this should be a good starting point.

Using the code

The code outlined in this article, is very simple. All you need is a .txt file with lines containing integers separated by commas "," or semi-colons ";" per line. The following sample data should be helpful:

123,3455,55 
1;3;44;555;66 
1324,55 
13,444 
2345,444,555,44
23455;5675;66

Copy the above lines into your .txt file and save it in a location "DriveLetter:\FolderOfChoice\yourfileName.txt".

Start Visual Studio NB for this solution I used VS2010.

Create a new Console Application and name it accordingly e.g., StringCal.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;

Now add the following code between:

namespace StringCalc
{
}
 namespace StringCalc
{
    class Program
    {
        static string theLine; //variable for holding the current line that has been read from the file
        static int[] theList; // array to hold integer values read from the theLine
        static int LineNumber = 1; //A count keeping the current line's number
        static int theSum; //Variable to hold the sum of the numbers successfully ready from the file
        static StreamReader file = new StreamReader(
          "DriveLetter:/[FolderOfYourChoice]/yourfileName.txt");
        // Input stream for the file containing data to be operated on
       
        /// <summary>
        /// The sample data to be contained in the file InputData.txt is as follows
        /// 123,3455,55
        ///1;3;44;555;66
        ///1324,55
        ///13,444
        ///2345,444,555,44
        ///23455;5675;66
        /// </summary>
        /// <param name="args"></param>

        static void Main(string[] args)
        {
            //Iterate through the file being read

            while ((theLine = file.ReadLine()) != null)
            {
                Add(theLine); // Call the Add method and pass current line
            }

            Console.ReadLine();

            file.Close(); //Release the file
        }
        public static void Add(string numbers)
        {
          
            if (numbers.Contains(";")) //Check if line contains semi-colon as the delimiter
            {
                theList = numbers.Split(';').Select(int.Parse).ToArray();
                //add input elements to array excluding the ; character
            }
            else if (numbers.Contains(",")) //Check if the line contains comma as the delimiter
            {
                theList = numbers.Split(',').Select(int.Parse).ToArray(); ;
                // add input elements to array excluding the , character
            }
            else
            {
                throw new ArgumentException();
            }
            theSum = theList.Sum();

            Console.WriteLine("The sum of the numbers entered at line : " + 
              LineNumber.ToString() + " is : " + theSum);
            LineNumber++;

        }
    }
}

I have not added instructions on the how to step by step, to those of you interested in checking the working solution simply download the attached completed solution and create the text file then populate it with the sample data given at the beginning of this article.

The Unit Test Project

using IUAStringCalculator;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using System;

namespace StringCalc
{
    /// <summary>
    ///This is a test class for ProgramTest and is intended
    ///to contain all ProgramTest Unit Tests
    ///</summary>
    [TestClass()]
    public class ProgramTest
    {
        private TestContext testContextInstance;

        /// <summary>
        ///Gets or sets the test context which provides
        ///information about and functionality for the current test run.
        ///</summary>
        public TestContext TestContext
        {
            get
            {
                return testContextInstance;
            }
            set
            {
                testContextInstance = value;
            }
        }

        #region Additional test attributes
        //
        //You can use the following additional attributes as you write your tests:
        //
        //Use ClassInitialize to run code before running the first test in the class
        //[ClassInitialize()]
        //public static void MyClassInitialize(TestContext testContext)
        //{
        //}
        //
        //Use ClassCleanup to run code after all tests in a class have run
        //[ClassCleanup()]
        //public static void MyClassCleanup()
        //{
        //}
        //
        //Use TestInitialize to run code before running each test
        //[TestInitialize()]
        //public void MyTestInitialize()
        //{
        //}
        //
        //Use TestCleanup to run code after each test has run
        //[TestCleanup()]
        //public void MyTestCleanup()
        //{
        //}
        //
        #endregion

        /// <summary>
        ///A test for Add
        ///</summary>
        [TestMethod()]
        [DeploymentItem("IUAStringCalculator.exe")]
        public void AddTest()
        {
            //Input String
            string numbers = "1234,8594,945,99";
            //Expected Result
            int expectedResult = 10872;

            Program_Accessor.Add(numbers);

            int theResult = Program_Accessor.theSum;

            Assert.AreEqual(theResult, expectedResult);
        }

        [TestMethod()]
        [DeploymentItem("IUAStringCalculator.exe")]
        [ExpectedException(typeof(FormatException))]
        public void AddTest_Must_Throw_FormatException()
        {
            //Must throw an Exception
            //Input String
            string numbers = "1234;756hd;945;33";

            //Act
            Program_Accessor.Add(numbers);
        }
    }
}

Points of Interest

I found this little exercise extremely enjoyable, especially with the way the <String>.Split(";").Select... worked. This saved a lot of long checks and validation on the string to integer conversion and passing the successful input to an array. Also note the use of the Sum() function on the Array of integers.

In writing the Unit tests I had more fun especially when testing the Exception part of it. I actually learnt that you can test for any occurrences of a particular type of Exception and.

History

  • Initial article and sample source code: 14/10/2013.

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