检查ArrayList是否包含具有等于特定值的属性的对象

时间:2016-01-15 16:13:21

标签: vb.net object arraylist contains

所以我在VB.net中有一个应用程序,它从表中提取数据并将其插入到arraylist中以便稍后使用。我想要做的是在将对象添加到arraylist之前,我想检查该arraylist以查看该对象是否存在,但我希望能够根据该对象的特定属性进行检查。

以下是我所说的一个例子:

让我们说我从表中提取以下列的信息: InvoiceNo | DateCharged |数量| TotalCharge

我有一个SQL语句从表中提取信息然后我使用数据读取器来查看信息。我的代码看起来有点像这样:

public void send(View v){
        Uri uri = new Uri.Builder().scheme("http").authority("sub.domain.nl").path("test.php")
                .appendQueryParameter("action", "sendMessage")
                .appendQueryParameter("idto", "18")
                .appendQueryParameter("idfrom", "36")
                .appendQueryParameter("type", "audio")
                .build();
        String urlString = uri.toString();
        new SendAudioTask().execute(urlString);
    }


    private class SendAudioTask extends AsyncTask<String, Integer, String> {
        @Override
        protected void onPreExecute() {
            super.onPreExecute();
        }

        @Override
        protected String doInBackground(String... params) {
            String url = params[0];
            File file = new File(Environment.getExternalStorageDirectory().getAbsolutePath(),
                    "/audio.3gpp");

            HttpResponse response = null;

            try {
                HttpClient httpclient = new DefaultHttpClient();

                HttpPost httppost = new HttpPost(url);

                InputStreamEntity reqEntity = new InputStreamEntity(
                        new FileInputStream(file), -1);
                reqEntity.setContentType("binary/octet-stream");
                reqEntity.setChunked(true); 
                httppost.setEntity(reqEntity);
                response = httpclient.execute(httppost);
            } catch (Exception e) {
                publishProgress(1);
            }
            return response.toString();
        }

        @Override
        protected void onProgressUpdate(Integer... values) {
            super.onProgressUpdate(values);
            Toast.makeText(MainActivity.this, "Dev message: = " + values[0], Toast.LENGTH_SHORT).show();
        }

        @Override
        protected void onPostExecute(String result) {
            super.onPostExecute(result);
            Toast.makeText(MainActivity.this, result, Toast.LENGTH_SHORT).show();
        }
    }

(exec_SQL_DR是clsDbobjManual类中的一个函数,它检查以确保SQL首先使用正确的语法并检查是否返回了记录,否则返回错误)

基本上我想要做的是在我向arraylist添加一个新对象之前我要检查一个对象是否已经存在于InvoiceNo是特定值的列表中,或者每次从表中提取的值确定没有重复。我希望列表中的每个InvoiceNo都有一个对象。

我正在寻找类似的东西:

Dim dbobjM As New clsDbobjManual()
If dbobjM.Exec_SQL_DR("SELECT InvoiceNo, DateCharged, Quantity, TotalCharges From Invoices") =  0 Then
  If dbobjM.DataReader.HasRows Then
    Dim invoicelist As New ArrayList(5000)
    Dim invoiceno As String = String.Empty
    Do While dbobjM.DataReader.Read()
      invoicelist.Add(New Invoice(dbobjM.DataReader.GetInt32(0), dbobjM.DataReader.Value(1), dbobjM.DataReader.GetInt32(2), dbobjM.DataReader.GetFloat(3)))
    Loop
  End If
End if

但我似乎无法找到我需要的东西,非常感谢任何帮助

2 个答案:

答案 0 :(得分:2)

无需使用过时的ArrayList:List会更好地为您服务。如果需要原因,请参阅ArrayList vs List<> in C# - 列表的优点也适用于VB.NET。

在没有看到你的clsDbobjManual或Invoice课程的情况下,我最后编写了最小的代码来完成你所做的事情,这基本上是invoices.Any(Function(i) i.InvoiceNo = inv.InvoiceNo)的检查,如果你有数据,你可以做列表(发票)。

请注意,我假设数据库中已使用了相应的数据类型 - 您应该使用Decimal类型来获取金钱,否则您最终可能会出现明显的舍入错误,并且日期应存储为DateTime,作为字符串。

Imports System.Data.SqlClient

Module Module1

    Class Invoice
        Property InvoiceNo As Integer
        Property DateCharged As DateTime
        Property Quantity As Integer
        Property TotalCharges As Decimal

        Sub New()
            ' empty constructor
        End Sub

        Sub New(invoiceNo As Integer, dateCharged As DateTime, quantity As Integer, totalCharges As Decimal)
            Me.InvoiceNo = invoiceNo
            Me.DateCharged = dateCharged
            Me.Quantity = quantity
            Me.TotalCharges = totalCharges
        End Sub

    End Class

    Function LoadData() As List(Of Invoice)
        Dim invoices As New List(Of Invoice)
        Dim connStr As String = "your connection string"

        Dim sql = "SELECT InvoiceNo, DateCharged, Quantity, TotalCharges From Invoices"

        Using sqlConn As New SqlConnection(connStr)
            Using sqlCmd As New SqlCommand(sql, sqlConn)
                Dim reader As SqlDataReader = sqlCmd.ExecuteReader()

                While reader.Read()
                    Dim inv As New Invoice(reader.GetInt32(0), reader.GetDateTime(1), reader.GetInt32(2), reader.GetDecimal(3))

                    If Not (invoices.Any(Function(i) i.InvoiceNo = inv.InvoiceNo)) Then
                        invoices.Add(inv)
                    Else
                        ' there is a duplicate invoice number
                    End If

                End While

            End Using
        End Using

        Return invoices

    End Function


    Sub Main()
        Dim uniqueInvoices As List(Of Invoice) = LoadData()
        ' uniqueInvoices now contains the data
    End Sub

End Module

如果你有一个批次的发票条目,你可能最好写一个SQL查询来做到这一点。

如果您实际上只想查找重复的发票号,可以使用SQL

SELECT [InvoiceNo]
FROM testTable
GROUP BY [InvoiceNo]
HAVING COUNT([InvoiceNo]) > 1

最后,请确保您使用的是Option Strict On,以免造成意外的数据类型错误 - 它们可能会大大减慢您的程序速度并导致错误的结果。

答案 1 :(得分:1)

您可以使用linq选择符合条件的对象。

Dim result = (From invoiceitem As Invoice
             In invoicelist 
             Where invoiceitem.InvoiceNo = dbobjM.DataReader.GetInt32(0)
             Select invoiceitem).ToList()

If Not result.Count > 0 Then
  invoicelist.Add(New Invoice(dbobjM.DataReader.GetInt32(0), dbobjM.DataReader.Value(1), dbobjM.DataReader.GetInt32(2), dbobjM.DataReader.GetFloat(3)))
End If