как сохранять данные в C#

466
21 сентября 2017, 13:13

Как сохранять данные в программе? Например, если у меня консольное приложение и я собираюсь считать свой бюджет и каждый раз, открывая программу я буду добавлять или отнимать деньги со своего бюджета.

Answer 1

Для начала можно попробовать сериализацию в XML. Привёл полный пример кода.

using System;
using System.IO;
using System.Xml.Serialization;
namespace ConsoleApp1
{
    class Program
    {
        static void Main(string[] args)
        {
            //string directory = Path.Combine(
            //    Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "ProgramName");
            string directory = Path.Combine("D:\\", "ProgramName");
            string file = Path.Combine(directory, "data.xml");
            Data data = new Data
            {
                Amount = 150m
            };
            Display(data, "Исходный вариант");
            try
            {
                if (!Directory.Exists(directory))
                {
                    Directory.CreateDirectory(directory);
                }
                Serializer.SaveToXml(file, data);
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex);
            }
            // Как будто читаем где-то в другом месте программы и не сразу же после записи
            // -----------------------------
            try
            {
                Data fromFile = null;
                if (File.Exists(file))
                {
                    fromFile = Serializer.LoadXml<Data>(file);
                }
                else
                {
                    fromFile = new Data();
                }
                Display(fromFile, "Прочитанный из файла");
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex);
            }
            Console.ReadKey();
        }
        private static void Display(Data data, string message)
        {
            Console.WriteLine(message + ". Amount: {0}", data.Amount);
        }
    }
    public class Data
    {
        public decimal Amount { get; set; }
    }
    public static class Serializer
    {
        public static void SaveToXml<T>(String fileName, T serializableObject)
        {
            XmlSerializer serializer = new XmlSerializer(typeof(T));
            using (TextWriter textWriter = new StreamWriter(fileName))
            {
                serializer.Serialize(textWriter, serializableObject);
            }
        }
        public static T LoadXml<T>(String fileName)
        {
            XmlSerializer serializer = new XmlSerializer(typeof(T));
            using (TextReader textReader = new StreamReader(fileName))
            {
                return (T)serializer.Deserialize(textReader);
            }
        }
    }
}
Answer 2

Существует много способов, но на мой взгляд самый простой - используя EntityFramework и подход Code First.

CodeFirst удобен тем, что вам ненужно самостоятельно создавать базу, она будет создана автоматически при первом входе в программу и дальше вы будете с ней работать.

Создаёте класс для работы с бюджетом. Все методы и необходимые поля (количество средств, операция со средствами, дата операции, описание)

Создаёте проект, подключаете EF через nuget package.

Далее создаём класс для работы с бюджетом. На моём примере вышло что-то такое

class BudgetUnit
{
    // Для работы с БД имя одного из полей должно заканчиваться на "id"
    public int Id { get; set; }
    public int changeInAmount { get; set; }
    public DateTime dt { get; set; }
    public string description { get; set; }
    // Также необходимо наличие пустого конструктора
    public BudgetUnit()
    { }        
    // Конструктор опционально
    public BudgetUnit(int changeInAmount, string description)
    {
       this.changeInAmount = changeInAmount;
       this.description = description;
       dt = DateTime.Now;
    }
}

Далее для работы с БД необходимо создать класс-контекст, почитать об этом можно например вот тут: https://msdn.microsoft.com/ru-ru/library/system.data.entity.dbcontext(v=vs.113).aspx

У меня получилось нечто такое:

using System.Data.Entity;
namespace Budget
{
  class BudgetUnitContext : DbContext
  {
    // Пустой конструктор. "DbConnection" - имя соединения настроим чуть 
    // ниже. 
    public BudgetUnitContext()
      : base("DbConnection")
    { }
    public DbSet<BudgetUnit> Units { get; set; }
  }
}

Далее необходимо зайти в App.config найти там закрывающий тег

</ConfigSections> 

и добавить после него строку подключения с именем "DbConnection":

<connectionStrings>
    <add name="DBConnection" connectionString="data source=
    (localdb)\MSSQLLocalDB;Initial Catalog=userstore.mdf;Integrated 
    Security=True;"
    providerName="System.Data.SqlClient"/>
</connectionStrings> 

Собственно это всё что нужно для сохранения данных в БД. Осталось использовать полученный механизм в программе:

static void Main(string[] args)
{
  // Внесение данных
  using (BudgetUnitContext db = new BudgetUnitContext())
  {
    BudgetUnit bu1 = new BudgetUnit(35000, "Аванс");
    BudgetUnit bu2 = new BudgetUnit(15000, "Сосед вернул долг");
    BudgetUnit bu3 = new BudgetUnit(-12000, "Покупка пароварки");
    db.Units.Add(bu1);
    db.Units.Add(bu2);
    db.Units.Add(bu3);
    db.SaveChanges();
    Console.WriteLine("Объекты добавлены");
    // Можно получать данные в этом же блоке, но для наглядности вынесу в отдельный
  }
  // Получение данных
  using (BudgetUnitContext db = new BudgetUnitContext())
  {
    var units = db.Units;
    Console.WriteLine("Список объектов");
    int money = 0;
    foreach (BudgetUnit u in units)
    {
      money += u.changeInAmount;
      Console.WriteLine("{0}: {1}, {2} - {3}, остаток средств {4}", u.Id, 
          u.dt, u.changeInAmount, u.description, money);
    }
  }
}
READ ALSO
Посоветуйте API для сохранение [требует правки]

Посоветуйте API для сохранение [требует правки]

Посоветуйте API для сохранение List, dictionary, string и тд в файл с возможностю редактирование - считывание в runtimeJson не подходит - не как не могу с ним...

200
Почему только статические методы?

Почему только статические методы?

Да, в C# очень обширная библиотекаНо почему то многие методы только статические

220
С# mvc 5 с базой данных

С# mvc 5 с базой данных

Я создал две моделиОдин для игроков, а второе для клубов

267
C# PictureBox неполное отображение содержимого

C# PictureBox неполное отображение содержимого

На форме WinForms создано 4 PictureBox, в цикле для каждого контрола устанавливается image из Dictionary где ключом является путь к файлу картинки:

261