Ответы пользователя по тегу C#
  • Можно ли устроиться C# программистом без специального образования?

    k1lex
    @k1lex
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    Поддержу мнение что главное здесь знания и умения. У нас в отделе из 7 человек программистов 1 с незаконченным образованием программиста, 2 физика, 1 учитель, 2 менеджера и 1 металлург.
    Насчет перехода в магистратуру - смотрите на свой уровень. Если считаете, что сможете работать и в армию не заберут, то ищите работу - любая работа лучше учебы. А если знаний недостаточно, то стоит и в магистратуру на программиста. Всё таки хорошая выпускная работа поможет повысить уровень
    Ответ написан
    Комментировать
  • Как настроить получение дополнительных свойств при использовании "своего" контрола?

    k1lex
    @k1lex Автор вопроса
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    На часть вопроса я всё таки нашел ответ самостоятельно.
    StringFormat не подхватывался, потому что при создании DependencyProperty у свойства "Value" использовался тип object. А StringFormat используется только для типа String. В виду того, что этот компонент нужен мне только для чтения, я поменял typeof(object) на typeof(string) и всё стало работать как нужно.
    Нормальным решением это конечно не назовешь. Но как говорил один герой в старом и добром мультфильме: "И так сойдет"
    Более подробно об этом написано на stackoverflow

    Насчет isReadOnly - завел для компонента еще одно свойство, аналогично первым двум (value и key). Работает.
    Ответ написан
    Комментировать
  • Как реализовать блокировки в базе данных MSSQL?

    k1lex
    @k1lex
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    Может многие меня не поддержат. Но у меня стояла задача разблокировать редактирование, при этом оставив просмотр для остальных. Оставлять одну только проверку версии казалось мало, а реализовывать через транзацию побоялся: неизвестно как будет себя вести изоляция, если ею раньше не пользовался.
    Реализация была через три дополнительных поля и пару процедур. Три на самом деле избыточно. Хватило бы и два. В общем этакий велосипед.
    Поля в заголовке:
    • Идентификатор пользователя UserEditGUID uniqueidentifier
    • Дата когда пользователь начал редактировать BeginEdit datetime
    • Не особо нужное поле isEdit bit


    И собственно процедура блокировки:
    ALTER PROCEDURE [dbo].[LockUnLockOrder]
    	@HeadGUID uniqueidentifier, @UserGUID  uniqueidentifier, @Lock bit
    	
    AS
    BEGIN
    	-- SET NOCOUNT ON added to prevent extra result sets from
    	-- interfering with SELECT statements.
    	SET NOCOUNT ON;
    	
    	if @HeadGUID is null or @UserGUID is null or @Lock is null 
    	begin
    	raiserror('Процедура LockUnLockOrder: Неинициализированный параметр',16,1)
    	return -1
    	end
    if V_ORDER.dbo.CheckEditStatus(@HeadGUID,@UserGUID) = 1
    begin
    	if 	@Lock = 1			
    	UPDATE [V_ORDER].[dbo].[OrderHeader]
    	SET isEdit = 1
    		,BeginEdit = getdate()
    		,UserEdit = @UserGUID
    	WHERE GUID = @HeadGUID
    	else 
    	if 	@Lock = 0			
    	UPDATE [V_ORDER].[dbo].[OrderHeader]
    	SET isEdit = 0
    		,BeginEdit = null
    		,UserEdit = null 
    	WHERE GUID = @HeadGUID
    	return 1
    end
    else raiserror('Невозможно изменить статус заказа',16,1)
    end


    И функция проверки возможности редактирования. Если пользователь открыл час назад, и не закрыл, то разрешение на редактирование выдается.
    -- =============================================
    -- Author:		k1lex
    -- Create date: 20160818
    -- Description:	функция возвращает разрешение редактирования заказа. 1 - можно редактировать. 0 - нельзя
    -- =============================================
    ALTER FUNCTION [dbo].[CheckEditStatus]
    (
    	-- Add the parameters for the function here
    	@HeadGUID uniqueidentifier, @UserGUID  uniqueidentifier
    )
    RETURNS bit
    AS
    BEGIN
    DECLARE @bit BIT
    
    IF (
    		SELECT COUNT(*)
    		FROM [V_ORDER].[dbo].[OrderHeader] O WITH (NOLOCK)
    		WHERE O.GUID = @HeadGUID
    			AND (ISNULL(O.IsReadOnly, 0) = 1 OR (O.userEdit != @UserGUID AND O.IsEdit = 1 AND DATEDIFF(HOUR, BeginEdit, GETDATE()) < 1)	
    			and [Status]=1
    			)
    		) = 0
    	SET @bit = 1
    ELSE
    	SET @bit = 0
    
    RETURN @bit
    END


    И поддержу Петр , что нужна проверка даты последнего изменения. На тот случай, если кто-то откроет, и вспомнит через три часа что открыл и отредактирует уже отредактированное.
    Ответ написан
    1 комментарий
  • C# Как найти блок текста в файле и заменить несколько повторяющихся строк?

    k1lex
    @k1lex
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    Сформируйте регулярные выражения
    А дальше воспользуйтесь простой заменой найденного на нужное вам
    Ответ написан
    Комментировать
  • Значение за пределами окна datagrid?

    k1lex
    @k1lex
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    По хорошему вам нужно изменить подход и работать с источником данных (о котором написал С Sharp ).
    DataGrid это всего лишь отображение и использовать его как DataGridView из WinForms не стоит.
    Создайте класс. Потом создайте ObserbvaleCollection из элементов этого класса.
    Свойству itemssource присвойте созданную коллекцию. Наслаждайтесь и
    спокойно пишите. Руки у вас будут развязаны. А на поиск подобных решений уйдет гора времени потраченных в итоге впустую.
    Ответ написан
    1 комментарий
  • C# как сравнить два списка List?

    k1lex
    @k1lex
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    Сравниваете два листа используя LINQ JOIN и выводите результат
    Ответ написан
    Комментировать
  • Как создать элементы ComboBox из SQLite?

    k1lex
    @k1lex
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    Сначала получите из базы в таблицу или в коллекцию результат вашего запроса. Причем, желательно не только имена, а идентификаторы тоже SELECT ID,NameGroup FROM Groupt
    Потом в свойстве DataSource укажите то куда вы данные засунули. В поле DisplayMember укажите NameGroup, а в ValueMember укажите ID.
    Таким образом когда пользователь выберет Имя группы, вы сможете считать ее идентификатор.
    Это для WinForms. Для WPF немного иначе.
    P.S. писал по памяти, мог где-нибудь ошибиться
    Ответ написан
    Комментировать
  • Почему не работает следующий Prepared запрос?

    k1lex
    @k1lex
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    Вы пытаетесь в качестве параметра передать таблицу. По моей практике это не очень возможно.
    Я в таком случае в транзации формирую времянку на сервере, передаю ее в нее таблицу и дальше делаю требуемые операции.
    Но сейчас смотря на ваш код я не очень понимаю зачем передавать таблицу на сервер что бы сервером из нее сделать SELECT.
    Может проще LINQ использовать?
    Ответ написан
  • Как конвертировать ObservableCollection в DataTable?

    k1lex
    @k1lex Автор вопроса
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    В итоге решил так (код взят из интернета).
    Относительно универсальный конвертер LIST в DataTable
    public DataTable ToDataTable<T>(List<T> items)
            {
                var tb = new DataTable(typeof(T).Name);
    
                PropertyInfo[] props = typeof(T).GetProperties(BindingFlags.Public | BindingFlags.Instance);
    
                foreach (PropertyInfo prop in props)
                {
                    Type t = GetCoreType(prop.PropertyType);
                    tb.Columns.Add(prop.Name, t);
                }
    
    
                foreach (T item in items)
                {
                    var values = new object[props.Length];
    
                    for (int i = 0; i < props.Length; i++)
                    {
                        values[i] = props[i].GetValue(item, null);
                    }
    
                    tb.Rows.Add(values);
                }    return tb;
            }
    
     public static bool IsNullable(Type t)
            {
                return !t.IsValueType || (t.IsGenericType && t.GetGenericTypeDefinition() == typeof(Nullable<>));
            }
    
     public static Type GetCoreType(Type t)
            {
                if (t != null && IsNullable(t))
                {
                    if (!t.IsValueType)
                    {
                        return t;
                    }
                    else
                    {
                        return Nullable.GetUnderlyingType(t);
                    }
                }
                else
                {
                    return t;
                }
            }
    Ответ написан
  • Как реализовать множественный фильтр данных?

    k1lex
    @k1lex Автор вопроса
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    Задачу решил сам поочередной проверкой условий.
    private void CollectionViewSource_Filter(object sender, FilterEventArgs e)
            {
                cgAssortment cgA = e.Item as cgAssortment;
                bool isAccept = true;
    
                if (cgA != null)
                {
                    try
                    {
                        isAccept = isAccept && (!this.cbOnLink.IsChecked.Value || (this.cbOnLink.IsChecked == true && (cgA.Group5GUID == null)));
                        isAccept = isAccept && (!this.cbInMatrix.IsChecked.Value || (this.cbInMatrix.IsChecked == true && (cgA.InMatrix == true)));
                        isAccept = isAccept && (!this.dgGoodsAllF1.IsChecked.Value || (this.dgGoodsAllF1.IsChecked.Value && cgA.Code.ToString() == this.dgGoodsAllT1.Text));
                        isAccept = isAccept && (!this.dgGoodsAllF2.IsChecked.Value || (this.dgGoodsAllF2.IsChecked.Value && (cgA.NameLong.ToUpper().Contains(this.dgGoodsAllT2.Text.ToUpper()))));
                        isAccept = isAccept && (!this.dgGoodsAllF3.IsChecked.Value || (this.dgGoodsAllF3.IsChecked.Value && (cgA.cgGroup2.NameLong.ToUpper().Contains(this.dgGoodsAllT3.Text.ToUpper()))));
                        isAccept = isAccept && (!this.dgGoodsAllF4.IsChecked.Value || (this.dgGoodsAllF4.IsChecked.Value && cgA.cgGroup3 != null && (cgA.cgGroup3.NameLong.ToUpper().Contains(this.dgGoodsAllT4.Text.ToUpper()))));
                        isAccept = isAccept && (!this.dgGoodsAllF5.IsChecked.Value || (this.dgGoodsAllF5.IsChecked.Value && cgA.cgGroup4 != null && (cgA.cgGroup4.NameLong.ToUpper().Contains(this.dgGoodsAllT5.Text.ToUpper()))));
                        isAccept = isAccept && (!this.dgGoodsAllF6.IsChecked.Value || (this.dgGoodsAllF6.IsChecked.Value && cgA.cgGroup5 != null && (cgA.cgGroup5.NameLong.ToUpper().Contains(this.dgGoodsAllT6.Text.ToUpper()))));
                        isAccept = isAccept && (!this.dgGoodsAllF7.IsChecked.Value || (this.dgGoodsAllF7.IsChecked.Value && cgA.cgGroup6 != null && (cgA.cgGroup6.NameLong.ToUpper().Contains(this.dgGoodsAllT7.Text.ToUpper()))));
                        isAccept = isAccept && (!this.dgGoodsAllF8.IsChecked.Value || (this.dgGoodsAllF8.IsChecked.Value && cgA.cgGroup7 != null && (cgA.cgGroup7.NameLong.ToUpper().Contains(this.dgGoodsAllT8.Text.ToUpper()))));
                        isAccept = isAccept && (!this.dgGoodsAllF9.IsChecked.Value || (this.dgGoodsAllF9.IsChecked.Value && cgA.cgGroup8 != null && (cgA.cgGroup8.NameLong.ToUpper().Contains(this.dgGoodsAllT9.Text.ToUpper()))));
                    }
                    catch (Exception er )
                    {
                        MessageBox.Show(er.Message);
                    }
                    e.Accepted = isAccept;
                }
            }


    P.S. Другим предложениям или объяснением как лучше сделать буду только рад.
    Ответ написан
  • Как быстро отсортировать и выбрать данные из 10000+ строк таблицы в C#?

    k1lex
    @k1lex
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    Еще вариант на уровне MS SQL распарсить файл, сделать необходимы отбор и передать данные в приложение.
    Ниже даю пример парсинга xml-файла в таблицу. Попробуйте переделать под себя
    Взял кусок из рабочего примера, где использовались пространства имен в файле. Если у вас их нет - удалите
    declare @xdat xml 
    
    -- получаем xml-файл
    SET @xdat  = (SELECT [DataXml]  FROM [TaskXml]  where TaskDocGUID='1A91AED3-B5DF-4526-81E9-D54C16BB82A7')
    
    if object_id('TempDb..#AllDataTable') > 0 drop table #AllDataTable
    SELECT Product.ref.value('declare namespace pref="http://fsrar.ru/WEGAIS/ProductRef";  (pref:Type/text())[1]', 'nvarchar(50)') AS [Type]
    	,Product.ref.value('declare namespace   pref="http://fsrar.ru/WEGAIS/ProductRef";  (pref:FullName/text())[1]', 'nvarchar(255)') AS FullName
    	,Product.ref.value('declare namespace   pref="http://fsrar.ru/WEGAIS/ProductRef";  (pref:ShortName/text())[1]', 'nvarchar(64)') AS ShortName
    	,Product.ref.query('declare namespace   pref="http://fsrar.ru/WEGAIS/ProductRef";   pref:Producer[1]') AS Producer
    	,Producer.ref.value('declare namespace  oref="http://fsrar.ru/WEGAIS/ClientRef";   (oref:ClientRegId/text())[1]', 'nvarchar(50)') AS ClientRegIdProducer
    	,Producer.ref.value('declare namespace  oref="http://fsrar.ru/WEGAIS/ClientRef";   (oref:INN/text())[1]', 'nvarchar(255)') AS INNProducer
    INTO #AllDataTable
    FROM @xdat.nodes('declare namespace rap="http://fsrar.ru/WEGAIS/ReplyAP";
    				  declare namespace ns="http://fsrar.ru/WEGAIS/WB_DOC_SINGLE_01";
    				  /ns:Documents/ns:Document/ns:ReplyAP/rap:Products/rap:Product') AS Product(ref)
    CROSS APPLY Product.ref.nodes('declare namespace  pref="http://fsrar.ru/WEGAIS/ProductRef";  pref:Producer') AS Producer(ref)
    
     SELECT * FROM #AllDataTable


    Код выше трудно читаем и понимаем. Попробую дать пример попроще

    -- формируем докумет
    DECLARE @xdat XML = (
    		SELECT TOP 5 GUID
    			,StatusDoc
    		FROM V_EGAIS.dbo.ActChargeOnHeader
    		FOR XML path('List')
    			,ROOT('Document')
    			,ELEMENTS
    			,type
    		)
    
    -- ниже пример того что получилось
    --  <Document>
    --  <List>
    --    <GUID>7F705894-441F-4B59-B6C4-0003579AE9BA</GUID>
    --    <LDM>2016-02-04T15:58:01.650</LDM>
    --  </List>
    --  <List>
    --    <GUID>D6EADAEB-AD45-4EB9-962D-0003B82CB431</GUID>
    --    <LDM>2016-02-04T15:59:51.723</LDM>
    --  </List>
    --  <List>
    --    <GUID>84BA1332-7C1F-4BAB-9923-0003D4B2CD7A</GUID>
    --    <LDM>2016-02-04T15:58:57.443</LDM>
    --  </List>
    --  <List>
    --    <GUID>A56EF787-3549-43DD-99E8-00043ED70C11</GUID>
    --    <LDM>2016-02-04T15:56:59.223</LDM>
    --  </List>
    --  <List>
    --    <GUID>16939553-7927-4221-B260-00044EBC225F</GUID>
    --    <LDM>2016-02-04T15:57:29.297</LDM>
    --  </List>
    --</Document>
    -- теперь производим выборку
    SELECT Document.ref.value('(GUID/text())[1]', 'nvarchar(255)') AS [GUID]
    	     ,Document.ref.value('(StatusDoc/text())[1]', 'int') AS StatusDoc
    FROM @xdat.nodes('/Document/List') AS Document(ref) -- тут мы показываем с какого раздела можно начинать брать данные.
    Ответ написан
    3 комментария
  • Как заполнить документ excel средствами c#?

    k1lex
    @k1lex
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    Если используете Microsoft.Office.Interop.Excel то что бы не было тормозов при заполнении передавайте данные сразу диапазоном. Вот один из моих методов, которыми пользуюсь.

    void ToExcel(DataTable dt1)
            {
                try
                {
                    Excel.Application EoXL;
                    Excel._Workbook EoWB;
                    Excel._Worksheet EoSheet;
                    Excel.Range excelRange;
                    EoXL = new Excel.Application();
                    EoXL.Visible = false;
                    EoWB = EoXL.Workbooks.Add(Type.Missing);
    
                    int TabRows = 1;
    
                    EoSheet = (Excel.Worksheet)EoWB.Worksheets.get_Item(1);//ссылка на лист excel
                    EoSheet.Name = "Отчет о кодах возвратных накладных";
                    EoSheet.PageSetup.Orientation = Excel.XlPageOrientation.xlLandscape;
    
                    int row = dt1.Rows.Count;
                    int col = dt1.Columns.Count;
    
    
                    EoSheet.Cells[1, 1] = "Префиксы возвратных накладных и счетов фактур подразделений";
                    EoSheet.Cells[1, 1].VerticalAlignment = Excel.XlVAlign.xlVAlignCenter;
                    EoSheet.Cells[1, 1].Font.Bold = true;
                    EoSheet.Cells[1, 1].Font.Size = 16;
    
                  
    
                    // передаем первую таблицу, заполняем ее в памяти и передаем целиком
                    object[,] dataExport = new object[row, col];
    
                    for (int i = 0; i < row; i++)
                    {
                        for (int j = 0; j < col; j++)
                        {
                            dataExport[i, j] = dt1.Rows[i][j];
                        }
    
                    }
    
    
                    excelRange = EoSheet.Range[EoSheet.Cells[2 + TabRows, 1], EoSheet.Cells[row + 1 + TabRows, col]];
                    excelRange.set_Value(Excel.XlRangeValueDataType.xlRangeValueDefault, dataExport);
                    excelRange.Borders.ColorIndex = 0;
    
    //этот кусок в качестве примера указания типа данных в ячейках
                    // excelRange = EoSheet.Range[EoSheet.Cells[2 + TabRows, 8], EoSheet.Cells[row + 1 + TabRows, 10]];
                    // excelRange.NumberFormat = "#,##0.00";
    
                    // формируем заголовок
                    ArrayList displayColumnExsel = new ArrayList();
    
    
                    foreach (DataColumn c in dt1.Columns)
                    {
    
                        displayColumnExsel.Add(c.ColumnName);
                    }
    
                    object[] dataExportH = new object[col];
                    for (int i = 0; i < col; i++)
                        dataExportH[i] = displayColumnExsel[i];
    
                    excelRange = EoSheet.Range[EoSheet.Cells[1 + TabRows, 1], EoSheet.Cells[1 + TabRows, col]];
                    excelRange.set_Value(Excel.XlRangeValueDataType.xlRangeValueDefault, dataExportH);
                    excelRange.Font.Bold = true;
                    excelRange.WrapText = true;
                    excelRange.Borders.ColorIndex = 0;
                    excelRange.VerticalAlignment = Excel.XlVAlign.xlVAlignCenter;
                    excelRange.HorizontalAlignment = Excel.XlHAlign.xlHAlignCenter;
                          
    
                   EoXL.Visible = true;
                }
                catch (Exception er)
                {
                    MessageBox.Show(er.Message, "Ошибка метода переноса таблиц", MessageBoxButton.OK, MessageBoxImage.Error);
                }
    
    
            }
    Ответ написан
    5 комментариев
  • Xaml - Как динамически изменять содержимое окна (пример: главное окно -> настройки)?

    k1lex
    @k1lex
    Программист торг. сети. C# (WPF, WinForms), T-SQL
    Способов много.
    Вот несколько:
    1. Используйте MVVM пример
    2. Создание UserControl с содержимым и загрузка их в контейнер типа ContentPresenter
    3. Pages
    4. Шаблоны содержимого
    5. TabPages тоже можно заюзать на крайний случай. В WPF вкладки можно скрывать.
    Ответ написан
    Комментировать