# count occurrances of a char in string #
PROC char count = (CHAR c, STRING str) INT:
   BEGIN
      INT count := 0;
      FOR i TO UPB str DO
	 IF c = str[i] THEN count +:= 1
	 FI
      OD;
      count
   END;

# split string on separator #
PROC char split = (STRING str, CHAR sep) FLEX[]STRING :
   BEGIN
      INT strlen := UPB str, cnt := 0;
      INT len, p;
      INT start := 1;
      [char count (sep, str) + 1] STRING list;
      WHILE start <= strlen ANDF char in string (sep, p, str[start:]) DO
	 p +:= start - 1;
	 list[cnt +:= 1] := str[start:p-1];
	 start := p + 1
      OD;
      IF cnt = 0 THEN list[cnt +:= 1] := str
      ELIF start <= UPB str + 1 THEN list[cnt +:= 1] := str[start:]
      FI;
      list
   END;

PROC join = ([]STRING words, STRING sep) STRING:
   IF UPB words > 0 THEN
      STRING str := words [1];
      FOR i FROM 2 TO UPB words DO
	 str +:= sep + words[i]
      OD;
      str
   ELSE
      ""
   FI;

# read a line from file #
PROC readline = (REF FILE f) STRING:
   BEGIN
      STRING line;
      get (f, line); new line (f);
      line
   END;

# Add one item to tuple #
OP +:= = (REF FLEX[]STRING tuple, STRING item) VOID:
   BEGIN
      [UPB tuple+1]STRING new;
      new[:UPB tuple] := tuple;
      new[UPB new] := item;
      tuple := new
   END;

# convert signed number TO INT #
OP TOINT = (STRING str) INT:
   BEGIN
      INT n := 0, sign := 1;
      FOR i TO UPB str WHILE sign /= 0 DO
	 IF is digit (str[i]) THEN n := n * 10 + ABS str[i] - ABS "0"
	 ELIF i = 1 AND str[i] = "-" THEN sign := -1
	 ELIF i /= 1 OR str[i] /= "+" THEN sign := 0
	 FI
      OD;
      n * sign
   END;

OP STR = (INT i) STRING: whole (i,0);

# The main program #
FILE foo;
open (foo, "CSV_data_manipulation.data", stand in channel);
FLEX[0]STRING header := char split (readline (foo), ",");
header +:= "SUM";
print ((join (header, ","), new line));
WHILE NOT end of file (foo) DO
   FLEX[0]STRING fields := char split (readline (foo), ",");
   INT sum := 0;
   FOR i TO UPB fields DO
      sum +:= TOINT fields[i]
   OD;
   fields +:= STR sum;
   print ((join (fields, ","), new line))
OD;
close (foo)


; data.csv
;
; C1,C2,C3,C4,C5
; 1,5,9,13,17
; 2,6,10,14,18
; 3,7,11,15,19
; 4,8,12,16,20

table: read.csv "data.csv"
data: []
loop table 'row [
    addable: ["SUM"]
    if row <> first table ->
        addable: @[to :string sum map row 'x [to :integer x]]

    'data ++ @[row ++ addable]
]

loop data 'row [
    loop row 'column ->
        prints pad column 6
    print ""
]


Loop, Read, Data.csv
{
    i := A_Index
    Loop, Parse, A_LoopReadLine, CSV
        Output .= (i=A_Index && i!=1 ? A_LoopField**2 : A_LoopField) (A_Index=5 ? "`n" : ",")
}
FileAppend, %Output%, NewData.csv


#!/usr/bin/awk -f
BEGIN { FS = OFS = "," }
NR==1 {
    print $0, "SUM"
    next
}
{
    sum = 0
    for (i=1; i<=NF; i++) {
        sum += $i
    }
    print $0, sum
}


OPTION COLLAPSE TRUE
OPTION DELIM ","

csv$ = LOAD$("data.csv")

DOTIMES AMOUNT(csv$, NL$)
    line$ = TOKEN$(csv$, _, NL$)

    IF _ = 1 THEN
        total$ = APPEND$(line$, 0, "SUM")
    ELSE
        line$ = CHANGE$(line$, _, STR$(_*10) )
        total$ = APPEND$(total$, 0, line$, NL$)
        total$ = APPEND$(total$, 0, STR$(LOOP(i, AMOUNT(line$), VAL(TOKEN$(line$, i)))) )
    FI
DONE

SAVE total$ TO "data.csv"
PRINT total$


OPEN "manip.csv" FOR INPUT AS #1
OPEN "manip2.csv" FOR OUTPUT AS #2

LINE INPUT #1, header$
PRINT #2, header$ + ",SUM"

WHILE NOT EOF(1)
    INPUT #1, c1, c2, c3, c4, c5
    sum = c1 + c2 + c3 + c4 + c5
    WRITE #2, c1, c2, c3, c4, c5, sum
WEND

CLOSE #1, #2
END


csvstr ← ⟨"C1,C2,C3,C4,C5", "1,5,9,13,17", "2,6,10,14,18", "3,7,11,15,19", "4,8,12,16,20"⟩

Split ← (⊢-˜¬×+`)∘=⟜','⊸⊔
strdata ← >Split¨csvstr
intdata ← •BQN¨⌾(1⊸↓) strdata
sums ← ⟨"SUMS"⟩ ∾+´˘ 1↓ intdata
done ← sums ∾˜˘ intdata


#define TITLE "CSV data manipulation"
#define URL "http://rosettacode.org/wiki/CSV_data_manipulation"

#define _GNU_SOURCE
#define bool int
#include <stdio.h>
#include <stdlib.h> /* malloc...*/
#include <string.h> /* strtok...*/
#include <ctype.h>
#include <errno.h>

/**
 * How to read a CSV file ?
 */

typedef struct {
	char * delim;
	unsigned int rows;
	unsigned int cols;
	char ** table;
} CSV;

/**
 * Utility function to trim whitespaces from left & right of a string
 */
int trim(char ** str) {
	int trimmed;
	int n;
	int len;

	len = strlen(*str);
	n = len - 1;
	/* from right */
	while((n>=0) && isspace((*str)[n])) {
		(*str)[n] = '\0';
		trimmed += 1;
		n--;
	}

	/* from left */
	n = 0;
	while((n < len) && (isspace((*str)[0]))) {
		(*str)[0] = '\0';
		*str = (*str)+1;
		trimmed += 1;
		n++;
	}
	return trimmed;
}

/**
 * De-allocate csv structure
 */
int csv_destroy(CSV * csv) {
	if (csv == NULL) { return 0; }
	if (csv->table != NULL) { free(csv->table); }
	if (csv->delim != NULL) { free(csv->delim); }
	free(csv);
	return 0;
}

/**
 * Allocate memory for a CSV structure
 */
CSV * csv_create(unsigned int cols, unsigned int rows) {
	CSV * csv;

	csv = malloc(sizeof(CSV));
	csv->rows = rows;
	csv->cols = cols;
	csv->delim = strdup(",");

	csv->table = malloc(sizeof(char *) * cols * rows);
	if (csv->table == NULL) { goto error; }

	memset(csv->table, 0, sizeof(char *) * cols * rows);

	return csv;

error:
	csv_destroy(csv);
	return NULL;
}

/**
 * Get value in CSV table at COL, ROW
 */
char * csv_get(CSV * csv, unsigned int col, unsigned int row) {
	unsigned int idx;
	idx = col + (row * csv->cols);
	return csv->table[idx];
}

/**
 * Set value in CSV table at COL, ROW
 */
int csv_set(CSV * csv, unsigned int col, unsigned int row, char * value) {
	unsigned int idx;
	idx = col + (row * csv->cols);
	csv->table[idx] = value;
	return 0;
}

void csv_display(CSV * csv) {
	int row, col;
	char * content;
	if ((csv->rows == 0) || (csv->cols==0)) {
		printf("[Empty table]\n");
		return ;
	}

	printf("\n[Table cols=%d rows=%d]\n", csv->cols, csv->rows);
	for (row=0; row<csv->rows; row++) {
		printf("[|");
		for (col=0; col<csv->cols; col++) {
			content = csv_get(csv, col, row);
            printf("%s\t|", content);
		}
        printf("]\n");
	}
	printf("\n");
}

/**
 * Resize CSV table
 */
int csv_resize(CSV * old_csv, unsigned int new_cols, unsigned int new_rows) {
	unsigned int cur_col,
				 cur_row,
				 max_cols,
				 max_rows;
	CSV * new_csv;
	char * content;
	bool in_old, in_new;

	/* Build a new (fake) csv */
	new_csv = csv_create(new_cols, new_rows);
	if (new_csv == NULL) { goto error; }

	new_csv->rows = new_rows;
	new_csv->cols = new_cols;

	max_cols = (new_cols > old_csv->cols)? new_cols : old_csv->cols;
	max_rows = (new_rows > old_csv->rows)? new_rows : old_csv->rows;

	for (cur_col=0; cur_col<max_cols; cur_col++) {
		for (cur_row=0; cur_row<max_rows; cur_row++) {
			in_old = (cur_col < old_csv->cols) && (cur_row < old_csv->rows);
			in_new = (cur_col < new_csv->cols) && (cur_row < new_csv->rows);

			if (in_old && in_new) {
				/* re-link data */
				content = csv_get(old_csv, cur_col, cur_row);
				csv_set(new_csv, cur_col, cur_row, content);
			} else if (in_old) {
				/* destroy data */
				content = csv_get(old_csv, cur_col, cur_row);
				free(content);
			} else { /* skip */ }
		}
	}
	/* on rows */
	free(old_csv->table);
	old_csv->rows = new_rows;
	old_csv->cols = new_cols;
	old_csv->table = new_csv->table;
	new_csv->table = NULL;
	csv_destroy(new_csv);

	return 0;

error:
	printf("Unable to resize CSV table: error %d - %s\n", errno, strerror(errno));
	return -1;
}

/**
 * Open CSV file and load its content into provided CSV structure
 **/
int csv_open(CSV * csv, char * filename) {
	FILE * fp;
	unsigned int m_rows;
	unsigned int m_cols, cols;
	char line[2048];
	char * lineptr;
	char * token;

	fp = fopen(filename, "r");
	if (fp == NULL) { goto error; }

	m_rows = 0;
	m_cols = 0;
	while(fgets(line, sizeof(line), fp) != NULL) {
 		m_rows += 1;
 		cols = 0;
 		lineptr = line;
 		while ((token = strtok(lineptr, csv->delim)) != NULL) {
 			lineptr = NULL;
 			trim(&token);
            cols += 1;
        	if (cols > m_cols) { m_cols = cols; }
            csv_resize(csv, m_cols, m_rows);
            csv_set(csv, cols-1, m_rows-1, strdup(token));
        }
	}

	fclose(fp);
	csv->rows = m_rows;
	csv->cols = m_cols;
	return 0;

error:
	fclose(fp);
	printf("Unable to open %s for reading.", filename);
	return -1;
}

/**
 * Open CSV file and save CSV structure content into it
 **/
int csv_save(CSV * csv, char * filename) {
	FILE * fp;
	int row, col;
	char * content;

	fp = fopen(filename, "w");
	for (row=0; row<csv->rows; row++) {
		for (col=0; col<csv->cols; col++) {
			content = csv_get(csv, col, row);
            fprintf(fp, "%s%s", content,
            		((col == csv->cols-1) ? "" : csv->delim) );
		}
        fprintf(fp, "\n");
	}

	fclose(fp);
	return 0;
}

/**
 * Test
 */
int main(int argc, char ** argv) {
	CSV * csv;

	printf("%s\n%s\n\n",TITLE, URL);

	csv = csv_create(0, 0);
	csv_open(csv, "fixtures/csv-data-manipulation.csv");
	csv_display(csv);

	csv_set(csv, 0, 0, "Column0");
	csv_set(csv, 1, 1, "100");
	csv_set(csv, 2, 2, "200");
	csv_set(csv, 3, 3, "300");
	csv_set(csv, 4, 4, "400");
	csv_display(csv);

	csv_save(csv, "tmp/csv-data-manipulation.result.csv");
	csv_destroy(csv);

	return 0;
}


using System.IO;
using System.Linq;

namespace CSV_data_manipulation
{
    class Program
    {
        static void Main()
        {
            var input = File.ReadAllLines("test_in.csv");
            var output = input.Select((line, i) =>
            {
                if (i == 0)
                    return line + ",SUM";
                var sum = line.Split(',').Select(int.Parse).Sum();
                return line + "," + sum;
            }).ToArray();
            File.WriteAllLines("test_out.csv", output);
        }
    }
}


#include <map>
#include <vector>
#include <iostream>
#include <fstream>
#include <utility>
#include <functional>
#include <string>
#include <sstream>
#include <algorithm>
#include <cctype>

class CSV
{
public:
    CSV(void) : m_nCols( 0 ), m_nRows( 0 )
    {}

    bool open( const char* filename, char delim = ',' )
    {
        std::ifstream file( filename );

        clear();
        if ( file.is_open() )
        {
            open( file, delim );
            return true;
        }

        return false;
    }

    void open( std::istream& istream, char delim = ',' )
    {
        std::string         line;

        clear();
        while ( std::getline( istream, line ) )
        {
            unsigned int nCol = 0;
            std::istringstream    lineStream(line);
            std::string           cell;

            while( std::getline( lineStream, cell, delim ) )
            {
                m_oData[std::make_pair( nCol, m_nRows )] = trim( cell );
                nCol++;
            }
            m_nCols = std::max( m_nCols, nCol );
            m_nRows++;
        }
    }

    bool save( const char* pFile, char delim = ',' )
    {
        std::ofstream ofile( pFile );
        if ( ofile.is_open() )
        {
            save( ofile );
            return true;
        }
        return false;
    }

    void save( std::ostream& ostream, char delim = ',' )
    {
        for ( unsigned int nRow = 0; nRow < m_nRows; nRow++ )
        {
            for ( unsigned int nCol = 0; nCol < m_nCols; nCol++ )
            {
                ostream << trim( m_oData[std::make_pair( nCol, nRow )] );
                if ( (nCol+1) < m_nCols )
                {
                    ostream << delim;
                }
                else
                {
                    ostream << std::endl;
                }
            }
        }
    }

    void clear()
    {
        m_oData.clear();
        m_nRows = m_nCols = 0;
    }

    std::string& operator()( unsigned int nCol, unsigned int nRow )
    {
        m_nCols = std::max( m_nCols, nCol+1 );
        m_nRows = std::max( m_nRows, nRow+1 );
        return m_oData[std::make_pair(nCol, nRow)];
    }

    inline unsigned int GetRows() { return m_nRows; }
    inline unsigned int GetCols() { return m_nCols; }

private:
    // trim string for empty spaces in begining and at the end
    inline std::string &trim(std::string &s)
    {

        s.erase(s.begin(), std::find_if(s.begin(), s.end(), std::not1(std::ptr_fun<int, int>(std::isspace))));
        s.erase(std::find_if(s.rbegin(), s.rend(), std::not1(std::ptr_fun<int, int>(std::isspace))).base(), s.end());
        return s;
    }

private:
    std::map<std::pair<unsigned int, unsigned int>, std::string> m_oData;

    unsigned int    m_nCols;
    unsigned int    m_nRows;
};

int main()
{
    CSV oCSV;

    oCSV.open( "test_in.csv" );
    oCSV( 0, 0 ) = "Column0";
    oCSV( 1, 1 ) = "100";
    oCSV( 2, 2 ) = "200";
    oCSV( 3, 3 ) = "300";
    oCSV( 4, 4 ) = "400";
    oCSV.save( "test_out.csv" );
    return 0;
}


(require '[clojure.data.csv :as csv]
         '[clojure.java.io :as io])

(defn add-sum-column [coll]
  (let [titles (first coll)
        values (rest coll)]
    (cons (conj titles "SUM")
      (map #(conj % (reduce + (map read-string %))) values))))

(with-open [in-file (io/reader "test_in.csv")]
  (doall
    (let [out-data (add-sum-column (csv/read-csv in-file))]
      (with-open [out-file (io/writer "test_out.csv")]
        (csv/write-csv out-file out-data)))))


       IDENTIFICATION DIVISION.
       PROGRAM-ID. CSV.
       AUTHOR.  Bill Gunshannon.
       INSTALLATION.  Home.
       DATE-WRITTEN.  19 December 2021.
      ************************************************************
      ** Program Abstract:
      **   CSVs are something COBOL does pretty well.
      **     The commented out CONCATENATE statements are a
      **     second method other than the STRING method.
      ************************************************************

       ENVIRONMENT DIVISION.
       CONFIGURATION SECTION.
           REPOSITORY.
           FUNCTION ALL INTRINSIC.

       INPUT-OUTPUT SECTION.
       FILE-CONTROL.
            SELECT CSV-File ASSIGN TO "csv.txt"
                 ORGANIZATION IS LINE SEQUENTIAL.
            SELECT Out-File ASSIGN TO "new.csv.txt"
                 ORGANIZATION IS LINE SEQUENTIAL.

       DATA DIVISION.

       FILE SECTION.

       FD  CSV-File
           DATA RECORD IS CSV-Record.
       01  CSV-Record.
           05 Field1                  PIC X(64).

       FD  Out-File
           DATA RECORD IS Out-Line.
       01  Out-Line   PIC X(80).

       WORKING-STORAGE SECTION.

       01 Eof                   PIC X     VALUE 'F'.

       01  CSV-Data.
           05  CSV-Col1             PIC 9(5).
           05  CSV-Col2             PIC 9(5).
           05  CSV-Col3             PIC 9(5).
           05  CSV-Col4             PIC 9(5).
           05  CSV-Col5             PIC 9(5).

        01  CSV-Sum                  PIC ZZZ9.
        01  CSV-Sum-Alpha
                REDEFINES     CSV-Sum  PIC X(4).

       PROCEDURE DIVISION.

       Main-Program.
           OPEN INPUT  CSV-File
           OPEN OUTPUT Out-File
           PERFORM Read-a-Record
           PERFORM Build-Header
           PERFORM UNTIL Eof = 'T'
              PERFORM Read-a-Record
              IF Eof NOT EQUAL 'T' PERFORM Process-a-Record
           END-PERFORM
           CLOSE CSV-File
           CLOSE Out-File
           STOP RUN.

       Read-a-Record.
           READ CSV-File
              AT END MOVE 'T' TO Eof
           END-READ.

        Build-Header.
      **    MOVE CONCATENATE(TRIM(CSV-Record), ",SUM"
      **        TO Out-Line.
            STRING TRIM(CSV-Record), ",SUM" INTO Out-Line.
            WRITE Out-Line.
            MOVE SPACES TO Out-Line.

        Process-a-Record.
            UNSTRING CSV-Record DELIMITED BY ',' INTO
                  CSV-Col1 CSV-Col2 CSV-Col3 CSV-Col4 CSV-Col5.
            COMPUTE CSV-Sum =
                  CSV-Col1 + CSV-Col2 + CSV-Col3 + CSV-Col4 + CSV-Col5.
      **    MOVE CONCATENATE(TRIM(CSV-Record), "," TRIM(CSV-Sum-Alpha))
      **        TO Out-Line.
            STRING TRIM(CSV-Record), "," TRIM(CSV-Sum-Alpha)
                   INTO Out-Line.
            WRITE Out-Line.
            MOVE SPACES TO Out-Line.

       END-PROGRAM.


(defun csvfile-to-nested-list (filename delim-char)
    "Reads the csv to a nested list, where each sublist represents a line."
  (with-open-file (input filename)
    (loop :for line := (read-line input nil) :while line
          :collect (read-from-string
                    (substitute #\SPACE delim-char
                                (format nil "(~a)~%" line))))))

(defun sublist-sum-list (nested-list)
  "Return a list with the sum of each list of numbers in a nested list."
  (mapcar (lambda (l) (if (every #'numberp l)
                          (reduce #'+ l) nil))
          nested-list))

(defun append-each-sublist (nested-list1 nested-list2)
  "Horizontally append the sublists in two nested lists. Used to add columns."
  (mapcar #'append nested-list1 nested-list2))

(defun nested-list-to-csv (nested-list delim-string)
  "Converts the nested list back into a csv-formatted string."
  (format nil (concatenate 'string "~{~{~2,'0d" delim-string "~}~%~}")
          nested-list))

(defun main ()
  (let* ((csvfile-path #p"projekte/common-lisp/example_comma_csv.txt")
         (result-path #p"results.txt")
         (data-list (csvfile-to-nested-list csvfile-path #\,))
         (list-of-sums (sublist-sum-list data-list))
         (result-header "C1,C2,C3,C4,C5,SUM"))

    (setf data-list    ; add list of sums as additional column
          (rest    ; remove old header
           (append-each-sublist data-list
                                (mapcar #'list list-of-sums))))
    ;; write to output-file
    (with-open-file (output result-path :direction :output :if-exists :supersede)
      (format output "~a~%~a"
              result-header (nested-list-to-csv data-list ",")))))
(main)


void main() {
    import std.stdio, std.csv, std.file, std.typecons, std.array,
           std.algorithm, std.conv, std.range;

    auto rows = "csv_data_in.csv".File.byLine;
    auto fout = "csv_data_out.csv".File("w");
    fout.writeln(rows.front);
    fout.writef("%(%(%d,%)\n%)", rows.dropOne
                .map!(r => r.csvReader!int.front.map!(x => x + 1)));
}


program CSV_data_manipulation;

{$APPTYPE CONSOLE}

uses
  System.SysUtils,
  System.IoUtils,
  System.Types;

type
  TStringDynArrayHelper = record helper for TStringDynArray
    function Sum: Integer;
  end;

{ TStringDynArrayHelper }

function TStringDynArrayHelper.Sum: Integer;
var
  value: string;
begin
  Result := 0;
  for value in self do
    Result := Result + StrToIntDef(value, 0);
end;

const
  FILENAME = './Data.csv';

var
  i: integer;
  Input, Row: TStringDynArray;

begin
  Input := TFile.ReadAllLines(FILENAME);
  for i := 0 to High(Input) do
  begin
    if i = 0 then
      Input[i] := Input[i] + ',SUM'
    else
    begin
      Row := Input[i].Split([',']);
      Input[i] := Input[i] + ',' + row.Sum.ToString;
    end;
  end;
  TFile.WriteAllLines(FILENAME, Input);
end.


;; CSV -> LISTS
(define (csv->row line)  (map (lambda(x) (or (string->number x) x)) (string-split line ",")))
(define (csv->table csv) (map  csv->row (string-split csv "\n")))

;; LISTS -> CSV
(define (row->csv row) (string-join row ","))
(define (table->csv header rows)
    (string-join  (cons (row->csv header) (for/list ((row rows)) (row->csv row))) "\n"))

(define (task file)
 (let*
 	((table (csv->table file))
 	(header (first table))
 	(rows (rest table)))

 	(table->csv
 		(append header "SUM") ;; add last column
 		(for/list ((row rows)) (append row (apply + row))))))


// Assumes a CSV file exists and has been sprayed to a Thor cluster
MyFileLayout := RECORD
STRING Field1;
STRING Field2;
STRING Field3;
STRING Field4;
STRING Field5;
END;

MyDataset := DATASET ('~Rosetta::myCSVFile', MyFileLayout,CSV(SEPARATOR(',')));

MyFileLayout Appended(MyFileLayout pInput):= TRANSFORM
  SELF.Field1 := pInput.Field1 +'x';
  SELF.Field2 := pInput.Field2 +'y';
  SELF.Field3 := pInput.Field3 +'z';
  SELF.Field4 := pInput.Field4 +'a';
  SELF.Field5 := pInput.Field5 +'b';
END ;

MyNewDataset := PROJECT(MyDataset,Appended(LEFT));
OUTPUT(myNewDataset,,'~Rosetta::myNewCSVFile',CSV,OVERWRITE);


defmodule Csv do
  defstruct header: "", data: "", separator: ","

  def from_file(path) do
    [header | data] = path
    |> File.stream!
    |> Enum.to_list
    |> Enum.map(&String.trim/1)

    %Csv{ header: header, data: data }
  end

  def sums_of_rows(csv) do
    Enum.map(csv.data, fn (row) -> sum_of_row(row, csv.separator) end)
  end

  def sum_of_row(row, separator) do
    row
    |> String.split(separator)
    |> Enum.map(&String.to_integer/1)
    |> Enum.sum
    |> to_string
  end

  def append_column(csv, column_header, column_data) do
    header = append_to_row(csv.header, column_header, csv.separator)

    data = [csv.data, column_data]
    |> List.zip
    |> Enum.map(fn ({ row, value }) ->
      append_to_row(row, value, csv.separator)
    end)

    %Csv{ header: header, data: data }
  end

  def append_to_row(row, value, separator) do
    row <> separator <> value
  end

  def to_file(csv, path) do
    body = Enum.join([csv.header | csv.data], "\n")

    File.write(path, body)
  end
end

csv = Csv.from_file("in.csv")
csv
|> Csv.append_column("SUM", Csv.sums_of_rows(csv))
|> Csv.to_file("out.csv")


-module( csv_data ).

-export( [change/2, from_binary/1, from_file/1, into_file/2, task/0] ).

change( CSV, Changes ) -> lists:foldl( fun change_foldl/2, CSV, Changes ).

from_binary( Binary ) ->
        Lines = binary:split( Binary, <<"\n">>, [global] ),
        [binary:split(X, <<",">>, [global]) || X <- Lines].

from_file( Name ) ->
        {ok, Binary} = file:read_file( Name ),
        from_binary( Binary ).

into_file( Name, CSV ) ->
        Binaries = join_binaries( [join_binaries(X, <<",">>) || X <- CSV], <<"\n">> ),
        file:write_file( Name, Binaries ).

task() ->
       CSV = from_file( "CSV_file.in" ),
       New_CSV = change( CSV, [{2,3,<<"23">>}, {4,4,<<"44">>}] ),
       into_file( "CSV_file.out", New_CSV ).

change_foldl( {Row_number, Column_number, New}, Acc ) ->
        {Row_befores, [Row_columns | Row_afters]} = split( Row_number, Acc ),
        {Column_befores, [_Old | Column_afters]} = split( Column_number, Row_columns ),
        Row_befores ++ [Column_befores ++ [New | Column_afters]] ++ Row_afters.

join_binaries( Binaries, Binary ) ->
        [_Last | Rest] = lists:reverse( lists:flatten([[X, Binary] || X <- Binaries]) ),
        lists:reverse( Rest ).

split( 1, List ) -> {[], List};
split( N, List ) -> lists:split( N - 1, List ).


--- Read CSV file and add columns headed with 'SUM'
--- with trace
-- trace(0)

include get.e
include std/text.e

function split(sequence s, integer c)
    sequence removables = " \t\n\r\x05\u0234\" "
    sequence out
    integer first, delim
    out = {}
    first = 1
    while first <= length(s) do
        delim = find_from(c,s,first)
        if delim = 0 then
            delim = length(s)+1
        end if
        out = append(out,trim(s[first..delim-1],removables))
        first = delim + 1
    end while
    return out
end function

procedure main()
    integer fn    -- the file number
    integer fn2   -- the output file number
    integer e     -- the number of lines read
    object line   -- the next line from the file
    sequence data = {} -- parsed csv data row
    sequence headerNames = {} -- array saving column names
    atom sum = 0.0     -- sum for each row
    sequence var  -- holds numerical data read

    -- First we try to open the file called "data.csv".
    fn = open("data.csv", "r")
    if fn = -1 then
        puts(1, "Can't open data.csv\n")
	-- abort();
    end if

    -- Then we create an output file for processed data.
    fn2 = open("newdata.csv", "w")
    if fn2 = -1 then
        puts(1, "Can't create newdata.csv\n")
    end if

    -- By successfully opening the file we have established that
    -- the file exists, and open() gives us a file number (or "handle")
    -- that we can use to perform operations on the file.

    e = 1
    while 1 do
        line = gets(fn)
        if atom(line) then
            exit
        end if
        data = split(line, ',')

        if (e=1) then
            -- Save the header labels and
	    -- write them to output file.
            headerNames = data
	    for i=1 to length(headerNames) do
	        printf(fn2, "%s,", {headerNames[i]})
	    end for
	    printf(fn2, "SUM\n")
        end if

        -- Run a sum for the numerical data.
        if (e >= 2) then
	    for i=1 to length(data) do
	        printf(fn2, "%s,", {data[i]})
		var = value(data[i])
		if var[1] = 0 then
		    -- data read is numerical
		    -- add to sum
		    sum = sum + var[2]
		end if
	    end for
            printf(fn2, "%g\n", {sum})
	    sum = 0.0
        end if
        e = e + 1
    end while

    close(fn)
    close(fn2)
end procedure

main()


open System.IO

[<EntryPoint>]
let main _ =
    let input = File.ReadAllLines "test_in.csv"
    let output =
        input
        |> Array.mapi (fun i line ->
            if i = 0 then line + ",SUM"
            else
                let sum = Array.sumBy int (line.Split(','))
                sprintf "%s,%i" line sum)
    File.WriteAllLines ("test_out.csv", output)
    0


USING: csv io.encodings.utf8 kernel math.parser sequences ;
IN: rosetta-code.csv-manipulation

: append-sum ( seq -- seq' )
    dup [ string>number ] map-sum number>string suffix ;

: csv-sums ( seq -- seq' )
    [ 0 = [ "SUM" suffix ] [ append-sum ] if ] map-index ;

"example.csv" utf8 [ file>csv csv-sums ] [ csv>file ] 2bi


\ csvsum.fs     Add a new column named SUM that contain sums from rows of CommaSeparatedValues
\ USAGE:
\       gforth-fast csvsum.fs -e "stdout stdin csvsum bye" <input.csv >output.csv

        CHAR ,  CONSTANT SEPARATOR
        3       CONSTANT DECIMALS
        1E1 DECIMALS S>D D>F F** FCONSTANT FSCALE

: colsum        ( ca u -- F: -- sum ;return SUM from CSV-string )
        0E0 OVER SWAP BOUNDS
        ?DO     ( a )
                I [email protected] SEPARATOR =
                IF      ( a )
                        I TUCK OVER - >FLOAT  IF F+ THEN
                        1+
                THEN
        LOOP    DROP
;
: f>string      ( -- ca u F: x -- )
        FSCALE F*
        F>D TUCK DABS <# DECIMALS 0 DO # LOOP [CHAR] . HOLD #S ROT SIGN #>
;
: rowC!+        ( offs char -- u+1  ;store CHAR at here+OFFS,increment offset )
        OVER HERE + C! 1+
;
: row$!+        ( offs ca u -- offs+u ;store STRING at here+OFFS,update offset )
        ROT 2DUP + >R HERE + SWAP MOVE R>
;
\ If run program with '-m 4G'option, we have practically 4G to store a row
: csvsum        ( fo fi --  ;write into FILEID-OUTPUT processed input from FILEID-INPUT )
        2DUP
        HERE UNUSED ROT READ-LINE THROW
        IF      ( fo fi fo u )
                HERE SWAP               ( fo fi fo ca u )
                SEPARATOR rowC!+
                s\" SUM" row$!+         ( fo fi fo ca u' )
                ROT WRITE-LINE THROW
                BEGIN   ( fo fi )
                        2DUP HERE UNUSED ROT READ-LINE THROW
                WHILE   ( fo fi fo u )
                        HERE SWAP                       ( fo fi fo ca u )
                        SEPARATOR rowC!+
                        HERE OVER colsum f>string       ( fo fi fo ca u ca' u' )
                        row$!+                          ( fo fi fo ca u'+u )
                        ROT WRITE-LINE THROW
                REPEAT
        THEN
        2DROP 2DROP
;


program rowsum
    implicit none
    character(:), allocatable :: line, name, a(:)
    character(20) :: fmt
    double precision, allocatable :: v(:)
    integer :: n, nrow, ncol, i

    call get_command_argument(1, length=n)
    allocate(character(n) :: name)
    call get_command_argument(1, name)
    open(unit=10, file=name, action="read", form="formatted", access="stream")
    deallocate(name)

    call get_command_argument(2, length=n)
    allocate(character(n) :: name)
    call get_command_argument(2, name)
    open(unit=11, file=name, action="write", form="formatted", access="stream")
    deallocate(name)

    nrow = 0
    ncol = 0
    do while (readline(10, line))
        nrow = nrow + 1

        call split(line, a)

        if (nrow == 1) then
            ncol = size(a)
            write(11, "(A)", advance="no") line
            write(11, "(A)") ",Sum"
            allocate(v(ncol + 1))
            write(fmt, "('(',G0,'(G0,:,''',A,'''))')") ncol + 1, ","
        else
            if (size(a) /= ncol) then
                print "(A,' ',G0)", "Invalid number of values on row", nrow
                stop
            end if

            do i = 1, ncol
                read(a(i), *) v(i)
            end do
            v(ncol + 1) = sum(v(1:ncol))
            write(11, fmt) v
        end if
    end do
    close(10)
    close(11)
contains
    function readline(unit, line)
        use iso_fortran_env
        logical :: readline
        integer :: unit, ios, n
        character(:), allocatable :: line
        character(10) :: buffer

        line = ""
        readline = .false.
        do
            read(unit, "(A)", advance="no", size=n, iostat=ios) buffer
            if (ios == iostat_end) return
            readline = .true.
            line = line // buffer(1:n)
            if (ios == iostat_eor) return
        end do
    end function

    subroutine split(line, array, separator)
        character(*) line
        character(:), allocatable :: array(:)
        character, optional :: separator
        character :: sep
        integer :: n, m, p, i, k

        if (present(separator)) then
            sep = separator
        else
            sep = ","
        end if

        n = len(line)
        m = 0
        p = 1
        k = 1
        do i = 1, n
            if (line(i:i) == sep) then
                p = p + 1
                m = max(m, i - k)
                k = i + 1
            end if
        end do
        m = max(m, n - k + 1)

        if (allocated(array)) deallocate(array)
        allocate(character(m) :: array(p))

        p = 1
        k = 1
        do i = 1, n
            if (line(i:i) == sep) then
                array(p) = line(k:i-1)
                p = p + 1
                k = i + 1
            end if
        end do
        array(p) = line(k:n)
    end subroutine
end program


' FB 1.05.0 Win64

Open "manip.csv" For Input As #1 ' existing CSV file
Open "manip2.csv" For Output As #2 ' new CSV file for writing changed data

Dim header As String
Line Input #1, header
header += ",SUM"
Print #2, header

Dim As Integer c1, c2, c3, c4, c5, sum

While Not Eof(1)
  Input #1, c1, c2, c3, c4, c5
  sum = c1 + c2 + c3 + c4 + c5
  Write #2, c1, c2, c3, c4, c5, sum
Wend

Close #1
Close #2


import io.{lines, PrintWriter}

data Table( header, rows )

def read( file ) =
  l = lines( file )

  def next = vector( l.next().split(',') )

  if l.isEmpty() then
    return Table( vector(), [] )

  header = next()
  rows = seq()

  while l.hasNext()
    rows += next()

  Table( header, rows.toList() )

def write( table, out ) =
  w = if out is String then PrintWriter( out ) else out

  w.println( table.header.mkString(',') )

  for r <- table.rows
    w.println( r.mkString(',') )

  if out is String
    w.close()

def updateRow( header, row, updates ) =
  r = dict( (header(i), row(i)) | i <- 0:header.length() )
  updates( r )
  vector( r(f) | f <- header )

def update( table, updates ) =
  Table( table.header, (updateRow(table.header, r, updates) | r <- table.rows).toList() )

def addColumn( table, column, updates ) =
  Table( table.header + [column], (updateRow(table.header + [column], r + [null], updates) | r <- table.rows).toList() )

t = addColumn( read('test.csv'), 'SUM', r -> r('SUM') = sum(int(v) | (_, v) <- r if v != null) )
write( t, 'test_out.csv' )
write( t, System.out )


Public Sub Form_Open()
Dim sData As String = File.Load("data.csv")
Dim sLine, sTemp As String
Dim sOutput As New String[]
Dim siCount As Short
Dim bLine1 As Boolean

For Each sLine In Split(sData, gb.NewLine)
  If Not bLine1 Then
    sLine &= ",SUM"
    sOutput.Add(sLine)
    bLine1 = True
    Continue
  End If
  For Each sTemp In Split(sLine)
    siCount += Val(sTemp)
  Next
  sOutput.Add(sLine & "," & Str(siCount))
  siCount = 0
Next

sData = ""

For Each sTemp In sOutput
  sData &= sTemp & gb.NewLine
  Print sTemp;
  Print
Next

File.Save(User.home &/ "CSVData.csv", sData)

End


package main

import (
	"encoding/csv"
	"log"
	"os"
	"strconv"
)

func main() {
	rows := readSample()
	appendSum(rows)
	writeChanges(rows)
}

func readSample() [][]string {
	f, err := os.Open("sample.csv")
	if err != nil {
		log.Fatal(err)
	}
	rows, err := csv.NewReader(f).ReadAll()
	f.Close()
	if err != nil {
		log.Fatal(err)
	}
	return rows
}

func appendSum(rows [][]string) {
	rows[0] = append(rows[0], "SUM")
	for i := 1; i < len(rows); i++ {
		rows[i] = append(rows[i], sum(rows[i]))
	}
}

func sum(row []string) string {
	sum := 0
	for _, s := range row {
		x, err := strconv.Atoi(s)
		if err != nil {
			return "NA"
		}
		sum += x
	}
	return strconv.Itoa(sum)
}

func writeChanges(rows [][]string) {
	f, err := os.Create("output.csv")
	if err != nil {
		log.Fatal(err)
	}
	err = csv.NewWriter(f).WriteAll(rows)
	f.Close()
	if err != nil {
		log.Fatal(err)
	}
}


def csv = []
def loadCsv = { source -> source.splitEachLine(/,/) { csv << it.collect { it } } }
def saveCsv = { target -> target.withWriter { writer -> csv.each { writer.println it.join(',') } } }

loadCsv new File('csv.txt')
csv[0][0] = 'Column0'
(1..4).each { i -> csv[i][i] = i * 100 }
saveCsv new File('csv_out.txt')


import Data.Array (Array(..), (//), bounds, elems, listArray)
import Data.List (intercalate)
import Control.Monad (when)
import Data.Maybe (isJust)

delimiters :: String
delimiters = ",;:"

fields :: String -> [String]
fields [] = []
fields xs =
  let (item, rest) = break (`elem` delimiters) xs
      (_, next) = break (`notElem` delimiters) rest
  in item : fields next

unfields :: Maybe (Array (Int, Int) String) -> [String]
unfields Nothing = []
unfields (Just a) = every fieldNumber $ elems a
  where
    ((_, _), (_, fieldNumber)) = bounds a
    every _ [] = []
    every n xs =
      let (y, z) = splitAt n xs
      in intercalate "," y : every n z

fieldArray :: [[String]] -> Maybe (Array (Int, Int) String)
fieldArray [] = Nothing
fieldArray xs =
  Just $ listArray ((1, 1), (length xs, length $ head xs)) $ concat xs

fieldsFromFile :: FilePath -> IO (Maybe (Array (Int, Int) String))
fieldsFromFile = fmap (fieldArray . map fields . lines) . readFile

fieldsToFile :: FilePath -> Maybe (Array (Int, Int) String) -> IO ()
fieldsToFile f = writeFile f . unlines . unfields

someChanges :: Maybe (Array (Int, Int) String)
            -> Maybe (Array (Int, Int) String)
someChanges =
  fmap (// [((1, 1), "changed"), ((3, 4), "altered"), ((5, 2), "modified")])

main :: IO ()
main = do
  a <- fieldsFromFile "example.txt"
  when (isJust a) $ fieldsToFile "output.txt" $ someChanges a


import Utils   # To get CSV procedures

procedure main(A)
    f := open(A[1]) | &input
    i := 1
    write(!f)   # header line(?)
    every csv := parseCSV(!f) do {
        csv[i+:=1] *:= 100
        write(encodeCSV(csv))
        }
end


   data=: (','&splitstring);.2 freads 'rc_csv.csv'       NB. read and parse data
   data=: (<'"spam"') (<2 3)} data                       NB. amend cell in 3rd row, 4th column (0-indexing)
   'rc_outcsv.csv' fwrites~ ;<@(','&joinstring"1) data   NB. format and write out amended data


import java.io.*;
import java.awt.Point;
import java.util.HashMap;
import java.util.Scanner;

public class CSV {

    private HashMap<Point, String> _map = new HashMap<Point, String>();
    private int _cols;
    private int _rows;

    public void open(File file) throws FileNotFoundException, IOException {
        open(file, ',');
    }

    public void open(File file, char delimiter)
            throws FileNotFoundException, IOException {
        Scanner scanner = new Scanner(file);
        scanner.useDelimiter(Character.toString(delimiter));

        clear();

        while(scanner.hasNextLine()) {
            String[] values = scanner.nextLine().split(Character.toString(delimiter));

            int col = 0;
            for ( String value: values ) {
                _map.put(new Point(col, _rows), value);
                _cols = Math.max(_cols, ++col);
            }
            _rows++;
        }
        scanner.close();
    }

    public void save(File file) throws IOException {
        save(file, ',');
    }

    public void save(File file, char delimiter) throws IOException {
        FileWriter fw = new FileWriter(file);
        BufferedWriter bw = new BufferedWriter(fw);

        for (int row = 0; row < _rows; row++) {
            for (int col = 0; col < _cols; col++) {
                Point key = new Point(col, row);
                if (_map.containsKey(key)) {
                    bw.write(_map.get(key));
                }

                if ((col + 1) < _cols) {
                    bw.write(delimiter);
                }
            }
            bw.newLine();
        }
        bw.flush();
        bw.close();
    }

    public String get(int col, int row) {
        String val = "";
        Point key = new Point(col, row);
        if (_map.containsKey(key)) {
            val = _map.get(key);
        }
        return val;
    }

    public void put(int col, int row, String value) {
        _map.put(new Point(col, row), value);
        _cols = Math.max(_cols, col+1);
        _rows = Math.max(_rows, row+1);
    }

    public void clear() {
        _map.clear();
        _cols = 0;
        _rows = 0;
    }

    public int rows() {
        return _rows;
    }

    public int cols() {
        return _cols;
    }

    public static void main(String[] args) {
        try {
            CSV csv = new CSV();

            csv.open(new File("test_in.csv"));
            csv.put(0, 0, "Column0");
            csv.put(1, 1, "100");
            csv.put(2, 2, "200");
            csv.put(3, 3, "300");
            csv.put(4, 4, "400");
            csv.save(new File("test_out.csv"));
        } catch (Exception e) {
        }
    }
}


(function () {
    'use strict';

    // splitRegex :: Regex -> String -> [String]
    function splitRegex(rgx, s) {
        return s.split(rgx);
    }

    // lines :: String -> [String]
    function lines(s) {
        return s.split(/[\r\n]/);
    }

    // unlines :: [String] -> String
    function unlines(xs) {
        return xs.join('\n');
    }

    // macOS JavaScript for Automation version of readFile.
    // Other JS contexts will need a different definition of this function,
    // and some may have no access to the local file system at all.

    // readFile :: FilePath -> maybe String
    function readFile(strPath) {
        var error = $(),
            str = ObjC.unwrap(
                $.NSString.stringWithContentsOfFileEncodingError(
                    $(strPath)
                    .stringByStandardizingPath,
                    $.NSUTF8StringEncoding,
                    error
                )
            );
        return error.code ? error.localizedDescription : str;
    }

    // macOS JavaScript for Automation version of writeFile.
    // Other JS contexts will need a different definition of this function,
    // and some may have no access to the local file system at all.

    // writeFile :: FilePath -> String -> IO ()
    function writeFile(strPath, strText) {
        $.NSString.alloc.initWithUTF8String(strText)
            .writeToFileAtomicallyEncodingError(
                $(strPath)
                .stringByStandardizingPath, false,
                $.NSUTF8StringEncoding, null
            );
    }

    // EXAMPLE - appending a SUM column

    var delimCSV = /,\s*/g;

    var strSummed = unlines(
        lines(readFile('~/csvSample.txt'))
        .map(function (x, i) {
            var xs = x ? splitRegex(delimCSV, x) : [];

            return (xs.length ? xs.concat(
                // 'SUM' appended to first line, others summed.
                i > 0 ? xs.reduce(
                    function (a, b) {
                        return a + parseInt(b, 10);
                    }, 0
                ).toString() : 'SUM'
            ) : []).join(',');
        })
    );

    return (
        writeFile('~/csvSampleSummed.txt', strSummed),
        strSummed
    );

})();


# Omit empty lines
def read_csv:
  split("\n")
  | map(if length>0 then split(",") else empty end) ;

# add_column(label) adds a summation column (with the given label) to
# the matrix representation of the CSV table, and assumes that all the
# entries in the body of the CSV file are, or can be converted to,
# numbers:
def add_column(label):
  [.[0] + [label],
   (reduce .[1:][] as $line
     ([]; ($line|map(tonumber)) as $line | . + [$line + [$line|add]]))[] ] ;

read_csv | add_column("SUM") | map(@csv)[]


using DataFrames, CSV

ifn = "csv_data_manipulation_in.dat"
ofn = "csv_data_manipulation_out.dat"

df = CSV.read(ifn)
df.SUM = sum.(eachrow(df))
CSV.write(ofn, df)


// version 1.1.3

import java.io.File

fun main(args: Array<String>) {
    val lines = File("example.csv").readLines().toMutableList()
    lines[0] += ",SUM"
    for (i in 1 until lines.size) {
        lines[i] += "," + lines[i].split(',').sumBy { it.toInt() }
    }
    val text = lines.joinToString("\n")
    File("example2.csv").writeText(text)  // write to new file
    println(text)  // print to console
}


----------------------------------------
-- Simplified CSV parser (without escape character support etc.).
-- First line is interrepted as header with column names.
-- @param {string} csvStr
-- @param {string} [sep=","] - single char as string
-- @param {string} [eol=RETURN]
-- @return {propList}
----------------------------------------
on parseSimpleCSVString (csvStr, sep, eol)
  if voidP(sep) then sep=","
  if voidP(eol) then eol = RETURN
  lines = explode(eol, csvStr)
  if lines.getLast()="" then lines.deleteAt(lines.count)
  res = [:]
  res[#header] = explode(sep, lines[1])
  res[#data] = []
  cnt = lines.count
  repeat with i = 2 to cnt
    res[#data].append(explodeBySingleChar(sep, lines[i]))
  end repeat
  return res
end

----------------------------------------
-- Simplified CSV creater (without escape character support etc.).
-- @param {propList} csvData
-- @param {string} [sep=","]
-- @param {string} [eol=RETURN]
-- @return {string}
----------------------------------------
on createSimpleCSVString (csvData, sep, eol)
  if voidP(sep) then sep=","
  if voidP(eol) then eol = RETURN
  res = ""
  put implode(sep, csvData[#header])&eol after res
  cnt = csvData[#data].count
  repeat with i = 1 to cnt
    put implode(sep, csvData[#data][i])&eol after res
  end repeat
  return res
end

----------------------------------------
-- Explodes string into list
-- @param {string} delim
-- @param {string} str
-- @return {list}
----------------------------------------
on explode (delim, str)
  if delim.length=1 then return explodeBySingleChar(delim, str)
  l = []
  if voidP(str) then return l
  dl = delim.length
  repeat while true
    pos = offset(delim, str)
    if pos=0 then exit repeat
    l.add(str.char[1..pos-1])
    delete char 1 to pos+dl-1 of str
  end repeat
  if pos=0 then pos = 1-dl
  l.add(str.char[pos+dl..str.length])
  return l
end

----------------------------------------
-- Explode string into list based on single char delimiter
-- (uses Lingo's build-in 'item' support, therefor faster)
-- @param {string} delim
-- @param {string} str
-- @return {list}
----------------------------------------
on explodeBySingleChar (delim, str)
  l = []
  if voidP(str) then return l
  od = _player.itemDelimiter
  _player.itemDelimiter = delim
  cnt = str.item.count
  repeat with i = 1 to cnt
    l.add(str.item[i])
  end repeat
  _player.itemDelimiter = od
  return l
end

----------------------------------------
-- Implodes list into string
-- @param {string} delim
-- @param {list} l
-- @return {string}
----------------------------------------
on implode (delim, l)
  str = ""
  cnt = l.count
  repeat with i = 1 to cnt
    put l[i]&delim after str
  end repeat
  delete char (str.length-delim.length+1) to str.length of str
  return str
end


local csv={}
for line in io.lines('file.csv') do
    table.insert(csv, {})
    local i=1
    for j=1,#line do
        if line:sub(j,j) == ',' then
            table.insert(csv[#csv], line:sub(i,j-1))
            i=j+1
        end
    end
    table.insert(csv[#csv], line:sub(i,j))
end

table.insert(csv[1], 'SUM')
for i=2,#csv do
    local sum=0
    for j=1,#csv[i] do
        sum=sum + tonumber(csv[i][j])
    end
    if sum>0 then
        table.insert(csv[i], sum)
    end
end

local newFileData = ''
for i=1,#csv do
    newFileData=newFileData .. table.concat(csv[i], ',') .. '\n'
end

local file=io.open('file.csv', 'w')
file:write(newFileData)


Module Checkit {
      Function Sum {
            Long c=0
            while not empty {
                  c+=number
            }
            =c
      }
      Document CSV$ = {C1,C2,C3,C4,C5
            1,5,9,13,17
            2,6,10,14,18
            3,7,11,15,19
            4,8,12,16,20
      }
      \\ export encoded to UTF-16LE
      Save.Doc CSV$, "data1.csv", 0
      \\ Open Wide read UTF-16LE
      \\ use standard colum sep. as ","
      \\ use standard decimal point char
      \\ use standard (non json style string)
      \\ True = use bare strings (without "")
      Input With "",,,true
      Write With"",,,true
      \\ for excel csv use Input With chr$(9),,true, true
      Open "data1.csv" for Wide Input as #M
      Open "data2.csv" for Wide Output as #M1
      Input #M, h1$, h2$, h3$, h4$, h5$
      Write #M1, h1$, h2$, h3$, h4$, h5$
      Print h1$, h2$, h3$, h4$, h5$

      While not Eof(#M) {
            Input #M, A1, A2, A3, A4, A5
            Write #M1, A1, A2, A3, A4, A5, Sum(A1, A2, A3, A4, A5)
            Print A1, A2, A3, A4, A5
      }
      close #M1
      Close #M
      Open "data2.csv" for Wide Input as #M
      Input #M, h1$, h2$, h3$, h4$, h5$
      Print h1$, h2$, h3$, h4$, h5$
      While not Eof(#M) {
            Input #M, A1, A2, A3, A4, A5, Sum
            Print A1, A2, A3, A4, A5, Sum
      }
      Close #M
}
Checkit


M := ImportMatrix("data.csv",source=csv);
M(..,6) := < "Total", seq( add(M[i,j], j=1..5), i=2..5 ) >;
ExportMatrix("data_out.csv",M,target=csv);


filename='data.csv';
fid = fopen(filename);
header = fgetl(fid);
fclose(fid);
X = dlmread(filename,',',1,0);

fid = fopen('data.out.csv','w+');
fprintf(fid,'%s,sum\n',header);
for k=1:size(X,1),
	fprintf(fid,"%i,",X(k,:));
	fprintf(fid,"%i\n",sum(X(k,:)));
end;
fclose(fid);


def sum(record)
        sum = 0

        for i in range(1, len(record) - 1)
                sum = sum + int(record ~ i)
        end for

        return sum
end def

open "file.csv"
add "SUM"

for i in range($dbsize, 1)
        (i ~ @"SUM") = sum(#i)
end for

write


/* NetRexx */
options replace format comments java crossref symbols

import org.apache.commons.csv.

-- =============================================================================
class RCsv public final

properties private constant
  NL           = String System.getProperty("line.separator")
  COL_NAME_SUM = String 'SUM, "integers"'
  CSV_IFILE    = 'data/csvtest_in.csv'
  CSV_OFILE    = 'data/csvtest_sumRexx.csv'

-- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
method main(args = String[]) public static
  Arg  = Rexx(args)
  iCvs = Reader null
  oCvs = Writer null
  parse arg ifile ofile .
  if ifile = '', ifile = '.' then ifile = CSV_IFILE
  if ofile = '', ofile = '.' then ofile = CSV_OFILE
  say textFileContentsToString(ifile)
  do
    iCvs = BufferedReader(FileReader(ifile))
    oCvs = BufferedWriter(FileWriter(ofile))
    processCsv(iCvs, oCvs);
  catch ex = IOException
    ex.printStackTrace();
  finally
    do
      if iCvs \= null then iCvs.close()
      if oCvs \= null then oCvs.close()
    catch ex = IOException
      ex.printStackTrace()
    end
  end
  say textFileContentsToString(ofile)
  return

-- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
method processCsv(iCvs = Reader, oCvs = Writer) public static binary signals IOException
  printer = CSVPrinter null
  do
    printer = CSVPrinter(oCvs, CSVFormat.DEFAULT.withRecordSeparator(NL))
    oCvsHeaders = java.util.List
    oCvsRecord = java.util.List
    records = CSVFormat.DEFAULT.withHeader(String[0]).parse(iCvs)
    irHeader = records.getHeaderMap()
    oCvsHeaders = ArrayList(Arrays.asList((irHeader.keySet()).toArray(String[0])))
    oCvsHeaders.add(COL_NAME_SUM)
    printer.printRecord(oCvsHeaders)
    recordIterator = records.iterator()
    record = CSVRecord
    loop while recordIterator.hasNext()
      record = CSVRecord recordIterator.next()
      oCvsRecord = record2list(record, oCvsHeaders)
      printer.printRecord(oCvsRecord)
      end
  finally
    if printer \= null then printer.close()
  end
  return

-- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
method record2list(record = CSVRecord, oCvsHeaders = java.util.List) private static binary returns java.util.List
  cvsRecord = java.util.List
  rMap = record.toMap()
  recNo = record.getRecordNumber()
  rMap = alterRecord(rMap, recNo)
  sum = summation(record.iterator())
  rMap.put(COL_NAME_SUM, sum)
  cvsRecord = ArrayList()
  loop ci = 0 to oCvsHeaders.size() - 1
    key = oCvsHeaders.get(ci)
    cvsRecord.add(rMap.get(key))
    end ci
  return cvsRecord

-- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
method alterRecord(rMap = Map, recNo = long) private static binary returns Map
    rv = int
    rg = Random(recNo)
    rv = rg.nextInt(50)
    ks = rMap.keySet().toArray(String[0])
    ix = rg.nextInt(ks.length)
    yv = long 0
    ky = ks[ix];
    xv = String rMap.get(ky)
    if xv \= null & xv.length() > 0 then do
      yv = Long.valueOf(xv).longValue() + rv
      rMap.put(ks[ix], String.valueOf(yv))
      end
    return rMap

-- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
method summation(iColumn = Iterator) private static
  sum = 0
  loop while iColumn.hasNext()
    nv = Rexx(String iColumn.next())
    if nv = null, nv.length() = 0, \nv.datatype('n') then nv = 0
    sum = sum + nv
    end
  return sum

-- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
method textFileContentsToString(filename) private static
    lineOut = ''
    fs = Scanner null
    do
      fs = Scanner(File(filename))
      lineOut = lineout || filename || NL
      loop while fs.hasNextLine()
        line = fs.nextLine()
        lineOut = lineout || line || NL
        end
    catch ex = FileNotFoundException
      ex.printStackTrace()
    finally
      if fs \= null then fs.close()
    end
    return lineOut


import strutils, streams

let
  csv = newFileStream("data.csv", fmRead)
  outf = newFileStream("data-out.csv", fmWrite)

var lineNumber = 1

while true:
  if atEnd(csv):
    break
  var line = readLine(csv)

  if lineNumber == 1:
    line.add(",SUM")
  else:
    var sum = 0
    for n in split(line, ","):
      sum += parseInt(n)
    line.add(",")
    line.add($sum)

  outf.writeLine(line)

  inc lineNumber


use System.IO.File;
use Data.CSV;

class CsvData {
  function : Main(args : String[]) ~ Nil {
    file_out : FileWriter;
    leaving {
      if(file_out <> Nil) {
        file_out->Close();
      };
    };

    if(args->Size() > 0) {
      file_name := args[0];
      csv := CsvTable->New(FileReader->ReadFile(file_name));
      if(csv->IsParsed()) {
        csv->AppendColumn("SUM");
        for(i := 1; i < csv->Size(); i += 1;) {
          row := csv->Get(i);
          sum := row->Sum(row->Size() - 1);
          row->Set("SUM", sum->ToString());
        };
      };

      output := csv->ToString();
      output->PrintLine();

      file_out := FileWriter->New("new-csv.csv");
      file_out->WriteString(output);
    };
  }
}


let list_add_last this lst =
  List.rev (this :: (List.rev lst))

let () =
  let csv = Csv.load "data.csv" in
  let fields, data =
    (List.hd csv,
     List.tl csv)
  in
  let fields =
    list_add_last "SUM" fields
  in
  let sums =
    List.map (fun row ->
      let tot = List.fold_left (fun tot this -> tot + int_of_string this) 0 row in
      list_add_last (string_of_int tot) row
    ) data
  in
  Csv.output_all (Csv.to_channel stdout) (fields :: sums)


\\ CSV data manipulation
\\ 10/24/16 aev
\\ processCsv(fn): Where fn is an input path and file name (but no actual extension).
processCsv(fn)=
{my(F, ifn=Str(fn,".csv"), ofn=Str(fn,"r.csv"), cn=",SUM",nf,nc,Vr,svr);
if(fn=="", return(-1));
F=readstr(ifn); nf=#F;
F[1] = Str(F[1],cn);
for(i=2, nf,
  Vr=stok(F[i],",");  if(i==2,nc=#Vr);
  svr=sum(k=1,nc,eval(Vr[k]));
  F[i] = Str(F[i],",",svr);
);\\fend i
for(j=1, nf, write(ofn,F[j]))
}

\\ Testing:
processCsv("c:\\pariData\\test");


program CSV_Data_Manipulation;
uses Classes, SysUtils;

var s: string;
    ts: tStringList;
    inFile,
    outFile: Text;
    Sum: integer;
    Number: string;

begin

  Assign(inFile,'input.csv');
  Reset(inFile);

  Assign(outFile,'result.csv');
  Rewrite(outFile);

  ts:=tStringList.Create;
  ts.StrictDelimiter:=True;

  // Handle the header
  ReadLn(inFile,s);                     // Read a line from input file
  ts.CommaText:=s;                      // Split it to lines
  ts.Add('SUM');                        // Add a line
  WriteLn(outFile,ts.CommaText);        // Reassemble it with comma as delimiter

  // Handle the data
  while not eof(inFile) do
  begin
    ReadLn(inFile,s);
    ts.CommaText:=s;

    Sum:=0;
    for Number in ts do
      Sum+=StrToInt(Number);

    ts.Add('%D',[Sum]);

    writeln(outFile, ts.CommaText);
  end;
  Close(outFile);
  Close(inFile);
  ts.Free;
end.


#!/usr/bin/perl
use warnings;
use strict;

use List::Util 'sum';

my @header = split /,/, <>;
# Remove the newline.
chomp $header[-1];

my %column_number;
for my $i (0 .. $#header) {
    $column_number{$header[$i]} = $i;
}
my @rows   = map [ split /,/ ], <>;
chomp $_->[-1] for @rows;

# Add 1 to the numbers in the 2nd column:
$_->[1]++ for @rows;

# Add C1 into C4:
$_->[ $column_number{C4} ] += $_->[ $column_number{C1} ] for @rows;

# Add sums to both rows and columns.
push @header, 'Sum';
$column_number{Sum} = $#header;

push @$_, sum(@$_) for @rows;
push @rows, [
                map  {
                    my $col = $_;
                    sum(map $_->[ $column_number{$col} ], @rows);
                } @header
            ];

# Print the output.
print join(',' => @header), "\n";
print join(',' => @$_), "\n" for @rows;


with javascript_semantics
constant tcsv = """
C1,C2,C3,C4,C5
1,5,9,13,17
2,6,10,14,18
3,7,11,15,19
4,8,12,16,20
"""
sequence lines = iff(platform()=JS?split(tcsv,"\n"):get_text("test.csv",GT_LF_STRIPPED))
for i=1 to length(lines) do
    lines[i] = split(trim(lines[i]),',')
end for
lines[1] = join(lines[1],',')&",SUM"
for i=2 to length(lines) do
    sequence s = deep_copy(lines[i]), t = {}
    for j=1 to length(s) do
        t &= scanf(s[j],"%d")[1][1]
    end for
--  s[rand(length(s))] = rand(100) -- (if you like)
    t &= sum(t)
    lines[i] = sprintf("%d,%d,%d,%d,%d,%d",t)
end for
lines = join(lines,'\n')
if platform()!=JS then
    integer fn = open("out.csv","w")
    puts(fn,lines)
    close(fn)
end if
puts(1,lines)


<?php

// fputcsv() requires at least PHP 5.1.0
// file "data_in.csv" holds input data
// the result is saved in "data_out.csv"
// this version has no error-checking

$handle = fopen('data_in.csv','r');
$handle_output = fopen('data_out.csv','w');
$row = 0;
$arr = array();

while ($line = fgetcsv($handle))
{
    $arr[] = $line;
}

//change some data to zeroes
$arr[1][0] = 0; // 1,5,9,13,17 => 0,5,9,13,17
$arr[2][1] = 0; // 2,6,10,14,18 => 2,0,10,14,18

//add sum and write file
foreach ($arr as $line)
{
    if ($row==0)
    {
        array_push($line,"SUM");
    }
    else
    {
        array_push($line,array_sum($line));
    }
    fputcsv($handle_output, $line);
    $row++;
}
?>


(in "data.csv"
   (prinl (line) "," "SUM")
   (while (split (line) ",")
      (prinl (glue "," @) "," (sum format @)) ) )


*process source xref attributes or(!);
 csv: Proc Options(Main);
 /*********************************************************************
 * 19.10.2013 Walter Pachl
 * 'erase d:\csv.out'
 * 'set dd:in=d:\csv.in,recsize(300)'
 * 'set dd:out=d:\csv.out,recsize(300)'
 * Say 'Input:'
 * 'type csv.in'
 * 'csv'
 * Say ' '
 * Say 'Output:'
 * 'type csv.out'
 *********************************************************************/
 Dcl in  Record Input;
 Dcl out Record Output;
 On Endfile(in) Goto part2;
 Dcl (INDEX,LEFT,SUBSTR,TRIM) Builtin;

 Dcl (i,j,p,m,n) Bin Fixed(31) Init(0);
 Dcl s Char(100) Var;
 Dcl iline(10) Char(100) Var;
 Dcl a(20,20) Char(10) Var;
 Dcl sum Dec Fixed(3);
 Dcl oline Char(100) Var;

 Do i=1 By 1;
   Read File(in) Into(s);
   iline(i)=s;
   m=i;
   Call sep((s));
   End;

 part2:
 Do i=1 To m;
   If i=1 Then
     oline=iline(1)!!','!!'SUM';
   Else Do;
     sum=0;
     Do j=1 To n;
       sum=sum+a(i,j);
       End;
     oline=iline(i)!!','!!trim(sum);
     End;
   Write File(out) From(oline);
   End;

 sep: Procedure(line);
 Dcl line Char(*) Var;
 loop:
 Do j=1 By 1;
   p=index(line,',');
   If p>0 Then Do;
     a(i,j)=left(line,p-1);
     line=substr(line,p+1);
     End;
   Else Do;
     a(i,j)=line;
     Leave loop;
     End;
   End;
 n=j;
 End;

 End;


## Create a CSV file
@"
C1,C2,C3,C4,C5
1,5,9,13,17
2,6,10,14,18
3,7,11,15,19
4,8,12,16,20
"@ -split "`r`n" | Out-File -FilePath .\Temp.csv -Force

## Import each line of the CSV file into an array of PowerShell objects
$records = Import-Csv -Path .\Temp.csv

## Sum the values of the properties of each object
$sums = $records | ForEach-Object {
    [int]$sum = 0
    foreach ($field in $_.PSObject.Properties.Name)
    {
        $sum += $_.$field
    }
    $sum
}

## Add a column (Sum) and its value to each object in the array
$records = for ($i = 0; $i -lt $sums.Count; $i++)
{
    $records[$i] | Select-Object *,@{Name='Sum';Expression={$sums[$i]}}
}

## Export the array of modified objects to the CSV file
$records | Export-Csv -Path .\Temp.csv -Force

## Display the object in tabular form
$records | Format-Table -AutoSize


test :- augment('test.csv', 'test.out.csv').

% augment( +InFileName, +OutFileName)
augment(InFile, OutFile)  :-
	open(OutFile, write, OutStream),
	( ( csv_read_file_row(InFile, Row, [line(Line)]),
	    % Row is of the form row( Item1, Item2, ....).
	    addrow(Row, Out),
	    csv_write_stream(OutStream, [Out], []),
	    fail
	  )
	; close(OutStream)
	).

% If the first item in a row is an integer, then append the sum;
% otherwise append 'SUM':
addrow( Term, NewTerm ) :-
	Term =.. [F | List],
	List = [X|_],
	(integer(X) -> sum_list(List, Sum) ; Sum = 'SUM'),
	append(List, [Sum], NewList),
	NewTerm =.. [F | NewList].


EnableExplicit

#Separator$ = ","

Define fInput$ = "input.csv"; insert path to input file
Define fOutput$ = "output.csv"; insert path to output file
Define header$, row$, field$
Define nbColumns, sum, i

If OpenConsole()
  If Not ReadFile(0, fInput$)
    PrintN("Error opening input file")
    Goto Finish
  EndIf

  If Not CreateFile(1, fOutput$)
    PrintN("Error creating output file")
    CloseFile(0)
    Goto Finish
  EndIf

  ; Read header row
  header$ = ReadString(0)
  ; Determine number of columns
  nbColumns = CountString(header$, ",") + 1
  ; Change header row
  header$ + #Separator$ + "SUM"
  ; Write to output file
  WriteStringN(1, header$)

  ; Read remaining rows, process and write to output file
  While Not Eof(0)
    row$ = ReadString(0)
    sum = 0
    For i = 1 To nbColumns
      field$ = StringField(row$, i, #Separator$)
      sum + Val(field$)
    Next
    row$ + #Separator$ + sum
    WriteStringN(1, row$)
  Wend

  CloseFile(0)
  CloseFile(1)

  Finish:
  PrintN("")
  PrintN("Press any key to close the console")
  Repeat: Delay(10) : Until Inkey() <> ""
  CloseConsole()
EndIf


import fileinput

changerow, changecolumn, changevalue = 2, 4, '"Spam"'

with fileinput.input('csv_data_manipulation.csv', inplace=True) as f:
    for line in f:
        if fileinput.filelineno() == changerow:
            fields = line.rstrip().split(',')
            fields[changecolumn-1] = changevalue
            line = ','.join(fields) + '\n'
        print(line, end='')


t:("IIIII";enlist ",")0: `:input.csv    / Read CSV file input.csv into table t
t:update SUM:sum value flip t from t    / Add SUM column to t
`:output.csv 0: csv 0: t                / Write updated table as CSV to output.csv


#lang racket
(require (planet neil/csv:1:=7) net/url)

(define make-reader
  (make-csv-reader-maker
   '((separator-chars              #\,)
     (strip-leading-whitespace?  . #t)
     (strip-trailing-whitespace? . #t))))

(define (all-rows port)
  (define read-row (make-reader port))
  (define head (append (read-row) '("SUM")))
  (define rows (for/list ([row (in-producer read-row '())])
                 (define xs (map string->number row))
                 (append row (list (~a (apply + xs))))))
  (define (->string row) (string-join row "," #:after-last "\n"))
  (string-append* (map ->string (cons head rows))))


my $csvfile = './whatever.csv';
my $fh = open($csvfile, :r);
my @header = $fh.get.split(',');
my @csv = map {[.split(',')]>>.Num}, $fh.lines;
close $fh;

my $out = open($csvfile, :w);
$out.say((@header,'SUM').join(','));
$out.say((@$_, [+] @$_).join(',')) for @csv;
close $out;


/* REXX ***************************************************************
* extend in.csv to add a column containing the sum of the lines' elems
* 21.06.2013 Walter Pachl
**********************************************************************/
csv='in.csv'
Do i=1 By 1 While lines(csv)>0
  l=linein(csv)
  If i=1 Then
    l.i=l',SUM'
  Else Do
    ol=l
    sum=0
    Do While l<>''
      Parse Var l e ',' l
      sum=sum+e
      End
    l.i=ol','sum
    End
  End
Call lineout csv
'erase' csv
Do i=1 To i-1
  Call lineout csv,l.i
  End


# Project : CSV data manipulation

load "stdlib.ring"
fnin = "input.csv"
fnout = "output.csv"
fpin = fopen(fnin,"r")
fpout = fopen(fnout,"r")
csv = read(fnin)
nr = 0
csvstr = ""

while not feof(fpin)
        sum = 0
        nr = nr + 1
        line = readline(fpin)
        if nr = 1
           line = substr(line,nl,"")
           line = line + ",SUM"
           csvstr = csvstr + line + windowsnl()
        else
           csvarr = split(line,",")
           for n = 1 to len(csvarr)
                sum = sum + csvarr[n]
           next
           line = substr(line,nl,"")
           line = line + "," + string(sum)
           csvstr = csvstr + line + windowsnl()
        ok
end
write(fnout,csvstr)
csvend = read(fnout)
fclose(fpin)
fclose(fpout)
see csvend + nl


require 'csv'
# read:
ar = CSV.table("test.csv").to_a #table method assumes headers and converts numbers if possible.

# manipulate:
ar.first << "SUM"
ar[1..-1].each{|row| row << row.sum}

# write:
CSV.open("out.csv", 'w') do |csv|
  ar.each{|line| csv << line}
end


csv$ = "C1,C2,C3,C4,C5
1,5,9,13,17
2,6,10,14,18
3,7,11,15,19
4,8,12,16,20
"

print csv$
dim csvData$(5,5)

for r = 1 to 5
  a$ = word$(csv$,r,chr$(13))
  for c = 1 to 5
    csvData$(r,c) = word$(a$,c,",")
  next c
next r

[loop]
input "Row to change:";r
input "Col to change;";c
if r > 5 or c > 5 then
  print "Row ";r;" or Col ";c;" is greater than 5"
  goto [loop]
end if
input "Change Row ";r;" Col ";c;" from ";csvData$(r,c);" to ";d$
csvData$(r,c) = d$
for r = 1 to 5
  for c = 1 to 5
    print cma$;csvData$(r,c);
    cma$ = ","
   next c
   cma$ = ""
   print
next r


V crc_table = [0] * 256
L(i) 256
   UInt32 rem = i
   L 8
      I rem [&] 1 != 0
         rem >>= 1
         rem (+)= EDB8'8320
      E
         rem >>= 1
   crc_table[i] = rem

F crc32(buf, =crc = UInt32(0))
   crc = (-)crc
   L(k) buf
      crc = (crc >> 8) (+) :crc_table[(crc [&] F'F) (+) k.code]
   R (-)crc

print(hex(crc32(‘The quick brown fox jumps over the lazy dog’)))


use std::error::Error;
use std::num::ParseIntError;
use csv::{Reader, Writer};

fn main() -> Result<(), Box<dyn Error>> {
    let mut reader = Reader::from_path("data.csv")?;
    let mut writer = Writer::from_path("output.csv")?;

    // headers() returns an immutable reference, so clone() before appending
    let mut headers = reader.headers()?.clone();
    headers.push_field("SUM");
    writer.write_record(headers.iter())?;

    for row in reader.records() {
        let mut row = row?;

        // `sum` needs the type annotation so that `parse::<i64>` knows what error type to return
        let sum: Result<_, ParseIntError> = row.iter().try_fold(0, |accum, s| {
            Ok(accum + s.parse::<i64>()?)
        });

        row.push_field(&sum?.to_string());
        writer.write_record(row.iter())?;
    }

    writer.flush()?;
    Ok(())
}


PRHEX	EQU  $FDDA ; <= REPLACE THIS WITH THE PRHEX ROUTINE FOR YOUR MACHINE

string	EQU  $EC
length	EQU  $EE
crc0	EQU  $FA
crc1	EQU  $FB
crc2	EQU  $FC
crc3	EQU  $FD
table0	EQU  $9200
table1	EQU  $9300
table2	EQU  $9400
table3	EQU  $9500
	ORG  $9114
	LDA #<text
	STA  string
	LDA #>text
	STA  string+1
	LDA #$2b ; length of text
	STA  length
	LDA #$00
	STA  length+1
	STA  crc0
	STA  crc1
	STA  crc2
	STA  crc3
	JSR  crc32
	LDA  crc3
	JSR  PRHEX
	LDA  crc2
	JSR  PRHEX
	LDA  crc1
	JSR  PRHEX
	LDA  crc0
	JMP  PRHEX
text
	ASC 'The quick brown fox jumps over the lazy dog'
	; ORG  $916E
crc32
	JSR  start
	LDY  string
	STX  string
loop
	LDA length
	BNE no_borrow
	LDA length+1
	BEQ ones_complement
	DEC length+1
no_borrow
	DEC length
	LDA (string),Y
	EOR  crc0
	TAX
	LDA  table0,X
	EOR  crc1
	STA  crc0
	LDA  table1,X
	EOR  crc2
	STA  crc1
	LDA  table2,X
	EOR  crc3
	STA  crc2
	LDA  table3,X
	STA  crc3
	INY
	BNE  loop
	INC  string+1
	BNE  loop
start
have_table
	LDX #$00
	BNE  loop4 ; LDX #$04 BNE ones_complement
loop256
	LDA #$00
	STA  table3,X
	STA  table2,X
	STA  table1,X
	TXA
	STA  table0,X
	LDY #$08
loop8
	LSR  table3,X
	ROR  table2,X
	ROR  table1,X
	ROR  table0,X
	BCC  no_xor
	LDA  table3,X
	EOR #$ED
	STA  table3,X
	LDA  table2,X
	EOR #$B8
	STA  table2,X
	LDA  table1,X
	EOR #$83
	STA  table1,X
	LDA  table0,X
	EOR #$20
	STA  table0,X
no_xor
	DEY
	BNE  loop8
	INX
	BNE  loop256
ones_complement
	LDX #$04
	STX  have_table+1 ; self-modify
loop4
	DEX
	LDA  crc0,X
	EOR #$FF
	STA  crc0,X
	TXA
	BNE loop4
	RTS


with Ada.Text_IO; use Ada.Text_IO;
with GNAT.CRC32; use GNAT.CRC32;
with Interfaces; use Interfaces;
procedure TestCRC is
   package IIO is new Ada.Text_IO.Modular_IO (Unsigned_32);
   crc : CRC32;
   num : Unsigned_32;
   str : String := "The quick brown fox jumps over the lazy dog";
begin
   Initialize (crc);
   Update (crc, str);
   num := Get_Value (crc);
   IIO.Put (num, Base => 16); New_Line;
end TestCRC;


print crc "The quick brown fox jumps over the lazy dog"


import scala.io.Source

object parseCSV extends App {

  val rawData = """|C1,C2,C3,C4,C5
		  		   |1,5,9,13,17
		  		   |2,6,10,14,18
		  		   |3,7,11,15,19
		  		   |20,21,22,23,24""".stripMargin

  val data = Seq((Source.fromString(rawData).getLines()).map(_.split(",")).toSeq: _*)

  val output = ((data.take(1).flatMap(x => x) :+ "SUM").mkString(",") +: // Header line
    data.drop(1).map(_.map(_.toInt)). // Convert per line each array of String to array of integer
    map(cells => (cells, cells.sum)). //Add sum column to assemble a tuple. Part 1 are original numbers, 2 is the sum
    map(part => s"${part._1.mkString(",")},${part._2}")).mkString("\n")

  println(output)
  /* Outputs:

C1,C2,C3,C4,C5,SUM
1,5,9,13,17,45
2,6,10,14,18,50
3,7,11,15,19,55
20,21,22,23,24,110

*/
}


[0:255]BITS crc_table;
BOOL crc_table_computed := FALSE;

PROC make_crc_table = VOID:
   BEGIN
      INT n, k;
      FOR n FROM 0 TO 255 DO
         BITS c := BIN n;
         FOR k TO 8 DO
            c := IF 32 ELEM c THEN
                    16redb88320 XOR (c SHR 1)
                 ELSE
                    c SHR 1
		 FI
	 OD;
	 crc_table[n] := c
      OD;
      crc_table_computed := TRUE
   END;

PROC update_crc = (BITS crc, STRING buf) BITS:
   BEGIN
      BITS c := crc XOR 16rffffffff;
      INT n;

      IF NOT crc_table_computed THEN make_crc_table FI;
      FOR n TO UPB buf DO
         c := crc_table[ABS ((c XOR BIN ABS buf[n]) AND 16rff)] XOR (c SHR 8)
      OD ;
      c XOR 16rffffffff
   END;

 PROC hex = (BITS x) STRING :
   BEGIN
      PROC hexdig = (BITS x) CHAR: REPR (IF ABS x ≤ 9 THEN ABS x + ABS "0"
                                         ELSE ABS x - 10 + ABS "a"
					 FI);
      STRING h := "";
      IF x = 16r0 THEN
	 h := "0"
      ELSE
	 BITS n := x;
	 WHILE h := hexdig (n AND 16rf) + h; n ≠ 16r0 DO
	    n := n SHR 4
	 OD
      FI;
      h
   END;

PROC crc = (STRING buf) BITS:
   update_crc(16r0, buf);

STRING s = "The quick brown fox jumps over the lazy dog";
print(("CRC32 OF ", s, " is: ", hex (crc (s)), newline))


$ include "seed7_05.s7i";

const proc: main is func
  local
    var file: input is STD_NULL;
    var array array string: csvData is 0 times 0 times "";
    var integer: line is 0;
  begin
    input := open(dir(PROGRAM) & "/csvDataManipulation.in", "r");
    while hasNext(input) do
      csvData &:= split(getln(input), ",");
    end while;
    csvData[3][3] := "X";
    for key line range csvData do
      writeln(join(csvData[line], ","));
    end for;
  end func;


// For test purposes, start by creating (or re-creating) the data file
put {{
C1,C2,C3,C4,C5
1,5,9,13,17
2,6,10,14,18
3,7,11,15,19
4,8,12,16,20
}} into file "myData.csv"

// Read the file as a list of lists (rather than as the default list of property lists)
put CSVValue(file "myData.csv", asLists:Yes) into csvData

insert "SUM" into item 1 of csvData -- add a new column heading

// Go through all of the data rows to add the sum
repeat with rowNum= 2 to the number of items in csvData
	insert the sum of item rowNum of csvData into item rowNum of csvData
end repeat

put csvData -- see the modified data as a list of lists

put CSVFormat of csvData into file "myData.csv"

put file "myData.csv" -- display the updated file contents


CRC32(str, enc = "UTF-8")
{
    l := (enc = "CP1200" || enc = "UTF-16") ? 2 : 1, s := (StrPut(str, enc) - 1) * l
    VarSetCapacity(b, s, 0) && StrPut(str, &b, floor(s / l), enc)
    CRC32 := DllCall("ntdll.dll\RtlComputeCrc32", "UInt", 0, "Ptr", &b, "UInt", s)
    return Format("{:#x}", CRC32)
}

MsgBox % CRC32("The quick brown fox jumps over the lazy dog")


#include <stdio.h>
#include <string.h>
#include <zlib.h>

int main()
{
	const char *s = "The quick brown fox jumps over the lazy dog";
	printf("%lX\n", crc32(0, (const void*)s, strlen(s)));

	return 0;
}


# Read
var csvfile = %f'data.csv';
var fh = csvfile.open_r;
var header = fh.line.trim_end.split(',');
var csv = fh.lines.map { .trim_end.split(',').map{.to_num} };
fh.close;

# Write
var out = csvfile.open_w;
out.say([header..., 'SUM'].join(','));
csv.each { |row| out.say([row..., row.sum].join(',')) };
out.close;


import delim input.csv, clear
replace c5=c3+c4
egen sum=rowtotal(c*)
drop if mod(c3,3)==0
export delim output.csv, replace


    /// <summary>
    /// Performs 32-bit reversed cyclic redundancy checks.
    /// </summary>
    public class Crc32
    {
        #region Constants
        /// <summary>
        /// Generator polynomial (modulo 2) for the reversed CRC32 algorithm.
        /// </summary>
        private const UInt32 s_generator = 0xEDB88320;
        #endregion

        #region Constructors
        /// <summary>
        /// Creates a new instance of the Crc32 class.
        /// </summary>
        public Crc32()
        {
            // Constructs the checksum lookup table. Used to optimize the checksum.
            m_checksumTable = Enumerable.Range(0, 256).Select(i =>
            {
                var tableEntry = (uint)i;
                for (var j = 0; j < 8; ++j)
                {
                    tableEntry = ((tableEntry & 1) != 0)
                        ? (s_generator ^ (tableEntry >> 1))
                        : (tableEntry >> 1);
                }
                return tableEntry;
            }).ToArray();
        }
        #endregion

        #region Methods
        /// <summary>
        /// Calculates the checksum of the byte stream.
        /// </summary>
        /// <param name="byteStream">The byte stream to calculate the checksum for.</param>
        /// <returns>A 32-bit reversed checksum.</returns>
        public UInt32 Get<T>(IEnumerable<T> byteStream)
        {
            try
            {
                // Initialize checksumRegister to 0xFFFFFFFF and calculate the checksum.
                return ~byteStream.Aggregate(0xFFFFFFFF, (checksumRegister, currentByte) =>
                          (m_checksumTable[(checksumRegister & 0xFF) ^ Convert.ToByte(currentByte)] ^ (checksumRegister >> 8)));
            }
            catch (FormatException e)
            {
                throw new CrcException("Could not read the stream out as bytes.", e);
            }
            catch (InvalidCastException e)
            {
                throw new CrcException("Could not read the stream out as bytes.", e);
            }
            catch (OverflowException e)
            {
                throw new CrcException("Could not read the stream out as bytes.", e);
            }
        }
        #endregion

        #region Fields
        /// <summary>
        /// Contains a cache of calculated checksum chunks.
        /// </summary>
        private readonly UInt32[] m_checksumTable;

        #endregion
    }


#include <algorithm>
#include <array>
#include <cstdint>
#include <numeric>

// These headers are only needed for main(), to demonstrate.
#include <iomanip>
#include <iostream>
#include <string>

// Generates a lookup table for the checksums of all 8-bit values.
std::array<std::uint_fast32_t, 256> generate_crc_lookup_table() noexcept
{
  auto const reversed_polynomial = std::uint_fast32_t{0xEDB88320uL};

  // This is a function object that calculates the checksum for a value,
  // then increments the value, starting from zero.
  struct byte_checksum
  {
    std::uint_fast32_t operator()() noexcept
    {
      auto checksum = static_cast<std::uint_fast32_t>(n++);

      for (auto i = 0; i < 8; ++i)
        checksum = (checksum >> 1) ^ ((checksum & 0x1u) ? reversed_polynomial : 0);

      return checksum;
    }

    unsigned n = 0;
  };

  auto table = std::array<std::uint_fast32_t, 256>{};
  std::generate(table.begin(), table.end(), byte_checksum{});

  return table;
}

// Calculates the CRC for any sequence of values. (You could use type traits and a
// static assert to ensure the values can be converted to 8 bits.)
template <typename InputIterator>
std::uint_fast32_t crc(InputIterator first, InputIterator last)
{
  // Generate lookup table only on first use then cache it - this is thread-safe.
  static auto const table = generate_crc_lookup_table();

  // Calculate the checksum - make sure to clip to 32 bits, for systems that don't
  // have a true (fast) 32-bit type.
  return std::uint_fast32_t{0xFFFFFFFFuL} &
    ~std::accumulate(first, last,
      ~std::uint_fast32_t{0} & std::uint_fast32_t{0xFFFFFFFFuL},
        [](std::uint_fast32_t checksum, std::uint_fast8_t value)
          { return table[(checksum ^ value) & 0xFFu] ^ (checksum >> 8); });
}

int main()
{
  auto const s = std::string{"The quick brown fox jumps over the lazy dog"};

  std::cout << std::hex << std::setw(8) << std::setfill('0') << crc(s.begin(), s.end()) << '\n';
}


package require struct::matrix
package require csv

proc addSumColumn {filename {title "SUM"}} {
    set m [struct::matrix]

    # Load the CSV in
    set f [open $filename]
    csv::read2matrix $f $m "," auto
    close $f

    # Add the column with the sums
    set sumcol [$m columns]
    $m add column $title
    for {set i 1} {$i < [$m rows]} {incr i} {
	# Fill out a dummy value
	$m set cell $sumcol $i 0
	$m set cell $sumcol $i [tcl::mathop::+ {*}[$m get row $i]]
    }

    # Write the CSV out
    set f [open $filename w]
    csv::writematrix $m $f
    close $f

    $m destroy
}

addSumColumn "example.csv"


$$ MODE DATA
$$ csv=*
C1,C2,C3,C4,C5
1,5,9,13,17
2,6,10,14,18
3,7,11,15,19
4,8,12,16,20
$$ MODE TUSCRIPT
LOOP/CLEAR n,line=csv
 IF (n==1) THEN
  line=CONCAT (line,",SUM")
 ELSE
  lineadd=EXCHANGE(line,":,:':")
  sum=SUM(lineadd)
  line=JOIN(line,",",sum)
 ENDIF
 csv=APPEND(csv,line)
ENDLOOP


(let [crc (new java.util.zip.CRC32)
      str "The quick brown fox jumps over the lazy dog"]
  (. crc update (. str getBytes))
  (printf "CRC-32('%s') = %s\n" str (Long/toHexString (. crc getValue))))


      *> tectonics: cobc -xj crc32-zlib.cob -lz
       identification division.
       program-id. rosetta-crc32.

       environment division.
       configuration section.
       repository.
           function all intrinsic.

       data division.
       working-storage section.
       01 crc32-initial        usage binary-c-long.
       01 crc32-result         usage binary-c-long unsigned.
       01 crc32-input.
          05 value "The quick brown fox jumps over the lazy dog".
       01 crc32-hex            usage pointer.

       procedure division.
       crc32-main.

      *> libz crc32
       call "crc32" using
           by value crc32-initial
           by reference crc32-input
           by value length(crc32-input)
           returning crc32-result
           on exception
               display "error: no crc32 zlib linkage" upon syserr
       end-call
       call "printf" using "checksum: %lx" & x"0a" by value crc32-result

      *> GnuCOBOL pointers are displayed in hex by default
       set crc32-hex up by crc32-result
       display 'crc32 of "' crc32-input '" is ' crc32-hex

       goback.
       end program rosetta-crc32.


@(coll)@{name /[^,]+/}@(end)
@(collect :vars (value sum))
@  (bind sum 0)
@  (coll)@{value /[^,]+/}@(set sum @(+ sum (int-str value)))@(end)
@(end)
@(output)
@  (rep)@name,@(last)[email protected](end)
@  (repeat)
@    (rep)@value,@(last)@[email protected](end)
@  (end)
@(end)


cat csv | while read S; do
 [ -z ${S##*C*} ] && echo $S,SUM || echo $S,`echo $S | tr ',' '+' | bc`
done


crc32 = do ->
  table =
    for n in [0..255]
      for [0..7]
        if n & 1
          n = 0xEDB88320 ^ n >>> 1
        else
          n >>>= 1
      n
  (str, crc = -1) ->
    for c in str
      crc = crc >>> 8 ^ table[(crc ^ c.charCodeAt 0) & 255]
    (crc ^ -1) >>> 0


(ql:quickload :ironclad)
(defun string-to-digest (str digest)
  "Return the specified digest for the ASCII string as a hex string."
  (ironclad:byte-array-to-hex-string
    (ironclad:digest-sequence digest
                              (ironclad:ascii-string-to-byte-array str))))

(string-to-digest "The quick brown fox jumps over the lazy dog" :crc32)


if set (a, open ("yourcsv.csv", "r")) < 0 then
  print "Cannot open \qyourcsv.csv\q"  ' open file a for reading
  end                                  ' abort on file opening errors
endif

if set (b, open ("mycsv.csv", "w")) < 0 then
  print "Cannot open \qmycsv.csv\q"    ' open file a for writing
  end                                  ' abort on file opening errors
endif

if read (a) = 0 then                   ' read the header line
  print "Unexpected end of file"       ' if it fails, write the error
  close a : close b : end              ' close files and terminate
endif
                                       ' process the header line
for c = 0 step 1                       ' don't know number of columns
  p = here()                           ' get input buffer position
  y = tok (ord (","))                  ' parse the first field
until p = here()                       ' until buffer position doesn't change
  write b, show (y);",";               ' write it out
next

write b, "Sum"                         ' add a column

do while read (a)                      ' read a line
  s = 0                                ' reset the sum
  for x = 0 to c-1                     ' read all columns
    y = iif (set (y, val (tok (ord (",")))) = info ("nil"), 0, y)
    s = s + y                          ' add value to sum
    write b, y;",";                    ' write the value
  next                                 ' next column
  write b, s                           ' write the sum
loop

close a : close b : end                ' close files and terminate


#
# csv data manipulation
#

# declare a string stream to hold lines
decl string<> lines

# open the file specified on the command line, halting
# execution if they didn't enter one. it will be created if
# it doesn't exist yet
decl file f
if (< (size args) 2)
        out "error: please specify a csv file" endl console
        stop
end if
f.create args<1>
f.open args<1>

# read in all lines from the file
set lines (f.readlines)

# append sum column to header
set lines<0> (+ lines<0> ",SUM")

# determine sums and append them
decl int i sum
for (set i 1) (< i (size lines)) (inc i)
        set sum 0
        for (decl int j) (< j (size (split lines<i> ","))) (inc j)
                set sum (int (+ sum (int (split lines<i> ",")<j>)))
        end for
        set lines<i> (+ lines<i> (+ "," sum))
end for

# delete the file, then create it again
f.delete args<1>
f.create args<1>

# output all lines to the file
for (set i 0) (< i (size lines)) (inc i)
        out lines<i> endl f
end for


MODULE BbtComputeCRC32;
IMPORT ZlibCrc32,StdLog;

PROCEDURE Do*;
VAR
	s: ARRAY 128 OF SHORTCHAR;
BEGIN
	s := "The quick brown fox jumps over the lazy dog";
	StdLog.IntForm(ZlibCrc32.CRC32(0,s,0,LEN(s$)),16,12,'0',TRUE);
	StdLog.Ln;
END Do;
END BbtComputeCRC32.


require "digest/crc32";

p Digest::CRC32.checksum("The quick brown fox jumps over the lazy dog").to_s(16)


void main() {
    import std.stdio, std.digest.crc;

    "The quick brown fox jumps over the lazy dog"
    .crc32Of.crcHexString.writeln;
}


Sub ReadCSV()
    Workbooks.Open Filename:="L:\a\input.csv"
    Range("F1").Value = "Sum"
    Range("F2:F5").Formula = "=SUM(A2:E2)"
    ActiveWorkbook.SaveAs Filename:="L:\a\output.csv", FileFormat:=xlCSV
    ActiveWindow.Close
End Sub


'Instatiate FSO.
Set objFSO = CreateObject("Scripting.FileSystemObject")
'Open the CSV file for reading. The file is in the same folder as the script and named csv_sample.csv.
Set objInCSV = objFSO.OpenTextFile(objFSO.GetParentFolderName(WScript.ScriptFullName) & "\csv_sample.csv",1,False)
'Set header status to account for the first line as the column headers.
IsHeader = True
'Initialize the var for the output string.
OutTxt = ""
'Read each line of the file.
Do Until objInCSV.AtEndOfStream
	line = objInCSV.ReadLine
	If IsHeader Then
		OutTxt = OutTxt & line & ",SUM" & vbCrLf
		IsHeader = False
	Else
		OutTxt = OutTxt & line & "," & AddElements(line) & vbCrLf
	End If
Loop
'Close the file.
objInCSV.Close
'Open the same file for writing.
Set objOutCSV = objFSO.OpenTextFile(objFSO.GetParentFolderName(WScript.ScriptFullName) & "\csv_sample.csv",2,True)
'Write the var OutTxt to the file overwriting existing contents.
objOutCSV.Write OutTxt
'Close the file.
objOutCSV.Close
Set objFSO = Nothing

'Routine to add each element in a row.
Function AddElements(s)
	arr = Split(s,",")
	For i = 0 To UBound(arr)
		AddElements = AddElements + CInt(arr(i))
	Next
End Function


program CalcCRC32;

{$APPTYPE CONSOLE}

uses
  System.SysUtils, System.ZLib;

var
  Data: AnsiString = 'The quick brown fox jumps over the lazy dog';
  CRC: UInt32;

begin
  CRC := crc32(0, @Data[1], Length(Data));
  WriteLn(Format('CRC32 = %8.8X', [CRC]));
end.


defmodule Test do
  def crc32(str) do
    IO.puts :erlang.crc32(str) |> Integer.to_string(16)
  end
end

Test.crc32("The quick brown fox jumps over the lazy dog")


-module(crc32).
-export([test/0]).
test() ->
  io:fwrite("~.16#~n",[erlang:crc32(<<"The quick brown fox jumps over the lazy dog">>)]).


File_Open("input.csv")
for (#1 = 0; #1 < 4; #1++) {
    Goto_Line(#1+2)                             // line (starting from line 2)
    if (#1) {
        Search(",", ADVANCE+COUNT, #1)          // column
    }
    #2 = Num_Eval()                             // #2 = old value
    Del_Char(Chars_Matched)                     // delete old value
    Num_Ins(#2+100, LEFT+NOCR)                  // write new value
}
File_Save_As("output.csv", OK+NOMSG)


CLOSE DATABASES ALL
SET SAFETY OFF
MODIFY FILE file1.csv NOEDIT
*!* Create a cursor with integer columns
CREATE CURSOR tmp1 (C1 I, C2 I, C3 I, C4 I, C5 I)
APPEND FROM file1.csv TYPE CSV
SELECT C1, C2, C3, C4, C5, C1+C2+C3+C4+C5 As sum ;
FROM tmp1 INTO CURSOR tmp2
COPY TO file2.csv TYPE CSV
MODIFY FILE file2.csv NOEDIT IN SCREEN
SET SAFETY ON


module Crc32 =

    open System

    // Generator polynomial (modulo 2) for the reversed CRC32 algorithm.
    let private s_generator = uint32 0xEDB88320

    // Generate lookup table
    let private lutIntermediate input =
        if (input &&& uint32 1) <> uint32 0
        then s_generator ^^^ (input >>> 1)
        else input >>> 1

    let private lutEntry input =
        {0..7}
        |> Seq.fold (fun acc x -> lutIntermediate acc) input

    let private crc32lut =
        [uint32 0 .. uint32 0xFF]
        |> List.map lutEntry

    let crc32byte (register : uint32) (byte : byte) =
        crc32lut.[Convert.ToInt32((register &&& uint32 0xFF) ^^^ Convert.ToUInt32(byte))] ^^^ (register >>> 8)

    // CRC32 of a byte array
    let crc32 (input : byte[]) =
        let result = Array.fold crc32byte (uint32 0xFFFFFFFF) input
        ~~~result

    // CRC32 from ASCII string
    let crc32OfAscii (inputAscii : string) =
        let bytes = System.Text.Encoding.ASCII.GetBytes(inputAscii)
        crc32 bytes

    // Test
    let testString = "The quick brown fox jumps over the lazy dog"
    printfn "ASCII Input: %s" testString
    let result = crc32OfAscii testString
    printfn "CRC32: 0x%x" result


IN: scratchpad USING: checksums checksums.crc32 ;
IN: scratchpad "The quick brown fox jumps over the lazy dog" crc32
               checksum-bytes hex-string .
"414fa339"


import "io" for File

var lines = File.read("rc.csv").split("\n").map { |w| w.trim() }.toList

var file = File.create("rc.csv") // overwrite existing file
file.writeBytes(lines[0] + ",SUM\n")
for (line in lines.skip(1)) {
    if (line != "") {
        var nums = line.split(",").map { |s| Num.fromString(s) }
        var sum = nums.reduce { |acc, n| acc + n }
        file.writeBytes(line + ",%(sum)\n")
    }
}
file.close()


#APPTYPE CONSOLE

PRINT HEX(CHECKSUM("The quick brown fox jumps over the lazy dog"))

PAUSE


: crc/ ( n -- n ) 8 0 do dup 1 rshift swap 1 and if $edb88320 xor then loop ;

: crcfill   256 0 do i crc/ , loop ;

create crctbl crcfill

: crc+ ( crc n -- crc' ) over xor $ff and  cells crctbl + @  swap 8 rshift xor ;

: crcbuf ( crc str len -- crc ) bounds ?do i [email protected] crc+ loop ;

$ffffffff s" The quick brown fox jumps over the lazy dog" crcbuf $ffffffff xor hex.  bye   \ $414FA339


module crc32_m
    use iso_fortran_env
    implicit none
    integer(int32) :: crc_table(0:255)
contains
    subroutine update_crc(a, crc)
        integer :: n, i
        character(*) :: a
        integer(int32) :: crc

        crc = not(crc)
        n = len(a)
        do i = 1, n
            crc = ieor(shiftr(crc, 8), crc_table(iand(ieor(crc, iachar(a(i:i))), 255)))
        end do
        crc = not(crc)
    end subroutine

    subroutine init_table
        integer :: i, j
        integer(int32) :: k

        do i = 0, 255
            k = i
            do j = 1, 8
                if (btest(k, 0)) then
                    k = ieor(shiftr(k, 1), -306674912)
                else
                    k = shiftr(k, 1)
                end if
            end do
            crc_table(i) = k
        end do
    end subroutine
end module

program crc32
    use crc32_m
    implicit none
    integer(int32) :: crc = 0
    character(*), parameter :: s = "The quick brown fox jumps over the lazy dog"
    call init_table
    call update_crc(s, crc)
    print "(Z8)", crc
end program


string  0;              \use zero-terminated strings
def     LF=$0A, EOF=$1A;
int     Val, Char;
char    Str(80);

proc    InField;
int     I;
[I:= 0;  Val:= 0;
loop    [Char:= ChIn(1);
        if Char=^, or Char=LF or Char=EOF then quit;
        Str(I):= Char;
        I:= I+1;
        if Char>=^0 and Char<=^9 then
                Val:= Val*10 + Char - ^0;
        ];
Str(I):= 0;
];

int     Sum;
[loop   [InField;
        Text(0, Str);
        if Char = LF then quit;
        ChOut(0, ^,);
        ];
Text(0, ",SUM");
CrLf(0);
loop    [Sum:= 0;
        loop    [InField;
                if Char = EOF then return;
                if rem(Val/5)=0 then Val:= Val*20;
                IntOut(0, Val);
                Sum:= Sum + Val;
                if Char = LF then quit;
                ChOut(0, ^,);
                ];
        Text(0, ",");
        IntOut(0, Sum);
        CrLf(0);
        ];
]


open #1, "manipy.csv", "r" //existing CSV file separated by spaces, not commas
open #2, "manip2.csv", "w" //new CSV file for writing changed data

line input #1 header$
header$ = header$ + ",SUM"
print #2 header$

while !eof(1)
    input #1 c1, c2, c3, c4, c5
    sum = c1 + c2 + c3 + c4 + c5
    print #2 c1, c2, c3, c4, c5, sum
wend

close #1
close #2
end


' version 18-03-2017
' compile with: fbc -s console

Function crc32(buf As String) As UInteger<32>

    Static As UInteger<32> table(256)
    Static As UInteger<32> have_table
    Dim As UInteger<32> crc, k
    Dim As ULong i, j

    If have_table = 0 Then
        For i = 0 To 255
            k = i
            For j = 0 To 7
                If (k And 1) Then
                    k Shr= 1
                    k Xor= &Hedb88320
                Else
                    k Shr= 1
                End If
                table(i) = k
            Next
        Next
        have_table = 1
    End If

    crc = Not crc ' crc = &Hffffffff

    For i = 0 To Len(buf) -1
        crc = (crc Shr 8) Xor table((crc And &hff) Xor buf[i])
    Next

    Return Not crc

End Function

' ------=< MAIN >=------

Dim As String l = "The quick brown fox jumps over the lazy dog"
Dim As UInteger<32> crc

Print "input = "; l
print
Print "The CRC-32 checksum = "; Hex(crc32(l), 8)

' empty keyboard buffer
While Inkey <> "" : Wend
Print : Print "hit any key to end program"
Sleep
End


package main

import (
    "fmt"
    "hash/crc32"
)

func main() {
    s := []byte("The quick brown fox jumps over the lazy dog")
    result := crc32.ChecksumIEEE(s)
    fmt.Printf("%X\n", result)
}


csvFile:=File("test.csv");
header:=csvFile.readln().strip(); // remove trailing "\n" and leading white space
listOfLines:=csvFile.pump(List,fcn(line){ line.strip().split(",").apply("toInt") });

newFile:=File("test2.csv","w");
newFile.writeln(header + ",sum");
listOfLines.pump(newFile.writeln,fcn(ns){ String(ns.concat(","),",",ns.sum()) });
newFile.close();


def crc32(byte[] bytes) {
    new java.util.zip.CRC32().with { update bytes; value }
}


import Data.Bits ((.&.), complement, shiftR, xor)
import Data.Word (Word32)
import Numeric (showHex)

crcTable :: Word32 -> Word32
crcTable = (table !!) . fromIntegral
  where
    table = ((!! 8) . iterate xf) <$> [0 .. 255]
    shifted x = shiftR x 1
    xf r
      | r .&. 1 == 1 = xor (shifted r) 0xedb88320
      | otherwise = shifted r

charToWord :: Char -> Word32
charToWord = fromIntegral . fromEnum

calcCrc :: String -> Word32
calcCrc = complement . foldl cf (complement 0)
  where
    cf crc x = xor (shiftR crc 8) (crcTable $ xor (crc .&. 0xff) (charToWord x))

crc32 :: String -> String
crc32 = flip showHex [] . calcCrc

main :: IO ()
main = putStrLn $ crc32 "The quick brown fox jumps over the lazy dog"


using StringTools;

class Main {
  static function main() {
    var data = haxe.io.Bytes.ofString("The quick brown fox jumps over the lazy dog");
    var crc = haxe.crypto.Crc32.make(data);
    Sys.println(crc.hex());
  }
}


link hexcvt,printf

procedure main()
   s := "The quick brown fox jumps over the lazy dog"
   a := "414FA339"
   printf("crc(%i)=%s - implementation is %s\n",
          s,r := crc32(s),if r == a then "correct" else "in error")
end

procedure crc32(s)      #: return crc-32 (ISO 3309, ITU-T V.42, Gzip, PNG) of s
static crcL,mask
initial {
   crcL := list(256)                            # crc table
   p := [0,1,2,4,5,7,8,10,11,12,16,22,23,26]    # polynomial terms
   mask := 2^32-1                               # word size mask
   every (poly := 0) := ior(poly,ishift(1,31-p[1 to *p]))
   every c := n := 0 to *crcL-1 do {            # table
      every 1 to 8 do
         c := iand(mask,
                   if iand(c,1) = 1 then
                      ixor(poly,ishift(c,-1))
                   else
                      ishift(c,-1)
                  )
      crcL[n+1] := c
      }
   }

   crc := ixor(0,mask)                          # invert bits
   every crc := iand(mask,
                     ixor(crcL[iand(255,ixor(crc,ord(!s)))+1],ishift(crc,-8)))
   return hexstring(ixor(crc,mask))             # return hexstring
end


import java.util.zip.* ;

public class CRCMaker {
   public static void main( String[ ] args ) {
      String toBeEncoded = new String( "The quick brown fox jumps over the lazy dog" ) ;
      CRC32 myCRC = new CRC32( ) ;
      myCRC.update( toBeEncoded.getBytes( ) ) ;
      System.out.println( "The CRC-32 value is : " + Long.toHexString( myCRC.getValue( ) ) + " !" ) ;
   }
}


(() => {
    'use strict';

    // --------------------- CRC-32 ----------------------

    // crc32 :: String -> Int
    const crc32 = str => {
        // table :: [Int]
        const table = enumFromTo(0)(255).map(
            n => take(9)(
                iterate(
                    x => (
                        x & 1 ? (
                            z => 0xEDB88320 ^ z
                        ) : identity
                    )(x >>> 1)
                )(n)
            )[8]
        );
        return chars(str).reduce(
            (a, c) => (a >>> 8) ^ table[
                (a ^ c.charCodeAt(0)) & 255
            ],
            -1
        ) ^ -1;
    };

    // ---------------------- TEST -----------------------
    // main :: IO ()
    const main = () =>
        showHex(
            crc32('The quick brown fox jumps over the lazy dog')
        );

    // --------------------- GENERIC ---------------------

    // chars :: String -> [Char]
    const chars = s =>
        s.split('');

    // enumFromTo :: Int -> Int -> [Int]
    const enumFromTo = m =>
        n => !isNaN(m) ? (
            Array.from({
                length: 1 + n - m
            }, (_, i) => m + i)
        ) : enumFromTo_(m)(n);

    // identity :: a -> a
    const identity = x =>
        // The identity function.
        x;

    // iterate :: (a -> a) -> a -> Gen [a]
    const iterate = f =>
        // An infinite list of repeated
        // applications of f to x.
        function* (x) {
            let v = x;
            while (true) {
                yield(v);
                v = f(v);
            }
        };

    // showHex :: Int -> String
    const showHex = n =>
        // Hexadecimal string for a given integer.
        '0x' + n.toString(16);

    // take :: Int -> [a] -> [a]
    // take :: Int -> String -> String
    const take = n =>
        // The first n elements of a list,
        // string of characters, or stream.
        xs => 'GeneratorFunction' !== xs
        .constructor.constructor.name ? (
            xs.slice(0, n)
        ) : [].concat.apply([], Array.from({
            length: n
        }, () => {
            const x = xs.next();
            return x.done ? [] : [x.value];
        }));

    // MAIN -------------
    const result = main();
    return (
        console.log(result),
        result
    );
})();


# Util.crc32('The quick brown fox jumps over the lazy dog').toString(16);


using Libz
println(string(Libz.crc32(UInt8.(b"The quick brown fox jumps over the lazy dog")), base=16))


// version 1.0.6

import java.util.zip.CRC32

fun main(args: Array<String>) {
    val text = "The quick brown fox jumps over the lazy dog"
    val crc = CRC32()
    with (crc) {
        update(text.toByteArray())
        println("The CRC-32 checksum of '$text' = ${"%x".format(value)}")
    }
}


crcObj = script("CRC").new()

crc32 = crcObj.crc32("The quick brown fox jumps over the lazy dog")

put crc32
-- <ByteArrayObject length = 4 ByteArray = 0x41, 0x4f, 0xa3, 0x39 >

put crc32.toHexString(1, crc32.length)
-- "41 4f a3 39"


local compute=require"zlib".crc32()
local sum=compute("The quick brown fox jumps over the lazy dog")
print(string.format("0x%x", sum))


Module CheckIt {
      Function PrepareTable {
            Dim Base 0, table(256)
            For i = 0 To 255 {
                    k = i
                    For j = 0 To 7 {
                              If binary.and(k,1)=1 Then {
                                  k =binary.Xor(binary.shift(k, -1) ,  0xEDB88320)
                              }  Else k=binary.shift(k, -1)
                    }
                    table(i) = k
             }
             =table()
      }
      crctable=PrepareTable()
      crc32= lambda crctable (buf$) -> {
                crc =0xFFFFFFFF
                For i = 0 To Len(buf$) -1
                     crc = binary.xor(binary.shift(crc, -8), array(crctable, binary.xor(binary.and(crc, 0xff), asc(mid$(buf$, i+1, 1)))))
                Next i
                =0xFFFFFFFF-crc
      }
      Print crc32("The quick brown fox jumps over the lazy dog")=0x414fa339
}
CheckIt


type="CRC32"; (*pick one out of 13 predefined hash types*)
StringForm[
"The "<>type<>" hash code of \"``\" is ``.",
s="The quick brown fox jumps over the lazy dog",
Hash[s,type,"HexString"]
]


/**
 <doc>CRC32 in Neko</doc>
**/

var int32_new = $loader.loadprim("[email protected]_new", 1)
var update_crc32 = $loader.loadprim("[email protected]_crc32", 4)

var crc = int32_new(0)
var txt = "The quick brown fox jumps over the lazy dog"

crc = update_crc32(crc, txt, 0, $ssize(txt))
$print(crc, "\n")


/* NetRexx */
options replace format comments java crossref symbols binary

import java.util.zip.CRC32

toBeEncoded = String("The quick brown fox jumps over the lazy dog")
myCRC = CRC32()
myCRC.update(toBeEncoded.getBytes())
say "The CRC-32 value is :" Long.toHexString(myCRC.getValue()) "!"

return


import strutils

type TCrc32* = uint32
const InitCrc32* = TCrc32(0xffffffff)

proc createCrcTable(): array[0..255, TCrc32] =
  for i in 0..255:
    var rem = TCrc32(i)
    for j in 0..7:
      if (rem and 1) > 0: rem = (rem shr 1) xor TCrc32(0xedb88320)
      else: rem = rem shr 1
    result[i] = rem

# Table created at compile time
const crc32table = createCrcTable()

proc crc32(s: string): TCrc32 =
  result = InitCrc32
  for c in s:
    result = (result shr 8) xor crc32table[(result and 0xff) xor byte(c)]
  result = not result

echo crc32("The quick brown fox jumps over the lazy dog").int64.toHex(8)