Pregunta

Tengo un cuadro de texto, cuadro combinado, botón y DataGridView en un formulario que se utiliza para buscar y devolver información del cliente desde una vista MSSQL (vCustomer). Funciona muy bien, pero sé que mi código puede ser más eficiente. Los cuatro elementos en el cuadro combinado representan columnas para buscar.

¿Hay una manera simple de convertir lo siguiente a LINQ dinámico a SQL? Soy nuevo en C #. Revisé algunas otras publicaciones, pero parece que no puedo hacer que funcione.

public partial class MainForm : Form
{
    public MainForm()
    {
        InitializeComponent();
    }

    private void MainForm_Load(object sender, EventArgs e)
    {
        // columns to filter for
        string[] list = new string[4];
        list[0] = "Name";
        list[1] = "CustomerAccountNo";
        list[2] = "Telephone";
        list[3] = "Postal";

        // bind to combobox
        cboColumn.DataSource = list;
        cboColumn.SelectedIndex = 0;
    }

    private void btnSearch_Click(object sender, EventArgs e)
    {

        try
        {
            Cursor.Current = Cursors.WaitCursor; 
            CustomerSearchDataContext db = new CustomerSearchDataContext();
            IEnumerable<vCustomer> customerQuery = null;
            switch (cboColumn.SelectedIndex)
            {
                case 0:
                    customerQuery = from c in db.vCustomers
                                    where c.Name.Contains(txtSearch.Text)
                                    orderby c.CustomerAccountNo descending
                                    select c;
                    break;
                case 1:
                    customerQuery = from c in db.vCustomers
                                    where c.Name.Contains(txtSearch.Text)
                                    orderby c.CustomerAccountNo descending
                                    select c;
                    break;
                case 2:
                    customerQuery = from c in db.vCustomers
                                    where c.Telephone.Contains(txtSearch.Text)
                                    orderby c.CustomerAccountNo descending
                                    select c;
                    break;
                case 3:
                    customerQuery = from c in db.vCustomers
                                    where c.Postal.Contains(txtSearch.Text)
                                    orderby c.CustomerAccountNo descending
                                    select c;
                    break;
            }
            customerBindingSource.DataSource = customerQuery;
            dataGridView1.DataSource = customerBindingSource;
            dataGridView1.Columns["CustomerId"].Visible = false;
        }
        catch (System.Data.SqlClient.SqlException ex)
        {
            MessageBox.Show("An Error Occured - " + ex.Message,"Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
        }
        finally
        {
            Cursor.Current = Cursors.Default; 
        }
    }
}
¿Fue útil?

Solución

Use [System.Linq.Dynamic][1].

Obtenga la condición de un método y úsela en una sola consulta.

    switch (choice)
    {
        case case1:
            condition = string.Format("{0}.Contains({1})", "Column", "Value"
            break;

Otros consejos

Hola Rony. Intenté su sugerencia y refactoré mi código (ver más abajo). Sin embargo, recibo un error: No existe ninguna propiedad o campo 'smith' en el tipo 'vCustomer' . Por cierto, el MessageBox.Show (condición); la línea devuelve Name.Contains (smith) que parece correcto.

¿Qué estoy haciendo mal? Perdón por ser un novato y gracias por tu ayuda.

Lo descubrí ... ¡necesitaba ajustar la cadena de búsqueda con comillas dobles! El código ha sido editado.

public partial class MainForm : Form
{
    public MainForm()
    {
        InitializeComponent();
    }
    private void MainForm_Load(object sender, EventArgs e)
    {
        // data column to filter against
        string[] list = new string[4];
        list[0] = "Name";
        list[1] = "CustomerAccountNo";
        list[2] = "Telephone";
        list[3] = "Postal";
        cboColumn.DataSource = list;
        cboColumn.SelectedIndex = 0;

        // left, right or middle search
        string[] list2 = new string[3];
        list2[0] = "Contains";
        list2[1] = "StartsWith";
        list2[2] = "EndsWith";
        cboFilterAtt.DataSource = list2;
        cboFilterAtt.SelectedIndex = 0;
    }

    private void btnSearch_Click(object sender, EventArgs e)
    {
        try
        {
            Cursor.Current = Cursors.WaitCursor; 
            CustomerSearchDataContext db = new CustomerSearchDataContext();
            //string condition = string.Format("{0}.{1}({2})", cboColumn.SelectedValue, cboFilterAtt.SelectedValue, txtSearch.Text);
            string condition = string.Format("{0}.{1}({2})", cboColumn.SelectedValue, cboFilterAtt.SelectedValue, "\"" + txtSearch.Text + "\"");
            MessageBox.Show(condition);
            var customerQuery = db.vCustomers.Where(condition).OrderBy("CustomerAccountNo");
            customerBindingSource.DataSource = customerQuery;
            dataGridView1.DataSource = customerBindingSource;
            dataGridView1.Columns["CustomerId"].Visible = false;
        }
        catch (System.Data.SqlClient.SqlException ex)
        {
            MessageBox.Show("An Error Occured - " + ex.Message,"Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
        }
        finally
        {
            Cursor.Current = Cursors.Default; 
        }
    }
}
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top