Vb6 在VB中使用稀疏矩阵
我正在用VisualBasic编写一个最小二乘法程序,该程序要求我处理44000个点,以找到一个超定解。我使用一个线性代数矩阵,它接受二维数组作为双矩阵。它允许我反转、转置和执行基本矩阵计算。问题是,当我输入超过3000点时,程序不断崩溃。我认为这与我的A(设计)矩阵中的零有关。我知道使用稀疏矩阵将通过删除包含零的列和行来帮助我,但我不知道应该如何在程序中实现这一点。有谁能帮我弄清楚如何在我正在使用的线性代数库中使用稀疏矩阵,或者我可以用什么代码让我的程序在不崩溃的情况下处理44000个点?我有时间限制,非常感谢您的帮助。 谢谢Vb6 在VB中使用稀疏矩阵,vb6,Vb6,我正在用VisualBasic编写一个最小二乘法程序,该程序要求我处理44000个点,以找到一个超定解。我使用一个线性代数矩阵,它接受二维数组作为双矩阵。它允许我反转、转置和执行基本矩阵计算。问题是,当我输入超过3000点时,程序不断崩溃。我认为这与我的A(设计)矩阵中的零有关。我知道使用稀疏矩阵将通过删除包含零的列和行来帮助我,但我不知道应该如何在程序中实现这一点。有谁能帮我弄清楚如何在我正在使用的线性代数库中使用稀疏矩阵,或者我可以用什么代码让我的程序在不崩溃的情况下处理44000个点?我有
S.P
在您自己的稀疏矩阵类()中尝试类似的操作
下面是一个用数组实现的快速而脏的稀疏矩阵类。Const
CHUNK\u SIZE
控制martix的“稀疏性”。数组重新分配是以2个边界的幂为单位进行的。只支持正索引
Option Explicit
DefObj A-Z
Private Declare Function ArrPtr Lib "msvbvm60" Alias "VarPtr" (Ptr() As Any) As Long
Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (dst As Any, src As Any, ByVal nBytes As Long)
Private Const CHUNK_SIZE As Long = 100
Private Type UcsColChunk
ColValue() As Double
End Type
Private Type UcsRowValue
ColChunk() As UcsColChunk
End Type
Private Type UcsRowChunk
RowValue() As UcsRowValue
End Type
Private m_uRowChunks() As UcsRowChunk
Property Get Cell(ByVal lRow As Long, ByVal lCol As Long) As Double
On Error Resume Next
Cell = m_uRowChunks(lRow \ CHUNK_SIZE).RowValue(lRow Mod CHUNK_SIZE).ColChunk(lCol \ CHUNK_SIZE).ColValue(lCol Mod CHUNK_SIZE)
End Property
Property Let Cell(ByVal lRow As Long, ByVal lCol As Long, ByVal dblValue As Double)
If pvPeek(ArrPtr(m_uRowChunks)) = 0 Then
ReDim m_uRowChunks(0 To pvCalcSize(lRow \ CHUNK_SIZE)) As UcsRowChunk
ElseIf UBound(m_uRowChunks) < lRow \ CHUNK_SIZE Then
ReDim Preserve m_uRowChunks(0 To pvCalcSize(lRow \ CHUNK_SIZE)) As UcsRowChunk
End If
With m_uRowChunks(lRow \ CHUNK_SIZE)
If pvPeek(ArrPtr(.RowValue)) = 0 Then
ReDim .RowValue(0 To CHUNK_SIZE - 1) As UcsRowValue
End If
With .RowValue(lRow Mod CHUNK_SIZE)
If pvPeek(ArrPtr(.ColChunk)) = 0 Then
ReDim .ColChunk(0 To pvCalcSize(lCol \ CHUNK_SIZE)) As UcsColChunk
ElseIf UBound(.ColChunk) < lCol \ CHUNK_SIZE Then
ReDim Preserve .ColChunk(0 To pvCalcSize(lCol \ CHUNK_SIZE)) As UcsColChunk
End If
With .ColChunk(lCol \ CHUNK_SIZE)
If pvPeek(ArrPtr(.ColValue)) = 0 Then
ReDim .ColValue(0 To CHUNK_SIZE - 1) As Double
End If
.ColValue(lCol Mod CHUNK_SIZE) = dblValue
End With
End With
End With
End Property
Private Function pvCalcSize(ByVal lSize As Long) As Long
pvCalcSize = 2 ^ (Int(Log(lSize + 1) / Log(2)) + 1) - 1
End Function
Private Function pvPeek(ByVal lPtr As Long) As Long
Call CopyMemory(pvPeek, ByVal lPtr, 4)
End Function
选项显式
DefObj A-Z
私有声明函数ArrPtr Lib“msvbvm60”别名“VarPtr”(Ptr()如有),长度为
私有声明子CopyMemory Lib“kernel32”别名“rtlmovemory”(dst为任意,src为任意,ByVal n字节为任意长度)
私有常量块大小(长=100)
私有类型UcsColChunk
ColValue()为双精度
端型
私有类型UcsRowValue
ColChunk()作为UcsColChunk
端型
私有类型UcsRowChunk
RowValue()作为UcsRowValue
端型
私有m_uRowChunks()作为UcsRowChunk
属性将单元格(ByVal lRow为Long,ByVal lCol为Long)获取为Double
出错时继续下一步
Cell=m\u uRowChunks(lRow\CHUNK\u SIZE).RowValue(lRow Mod CHUNK\u SIZE).ColChunk(lCol\CHUNK\u SIZE).ColValue(lCol Mod CHUNK\u SIZE)
端属性
属性Let单元格(ByVal lRow为Long,ByVal lCol为Long,ByVal dblValue为Double)
如果pvPeek(ArrPtr(m_uRowChunks))=0,则
将m_uRowChunks(0到pvCalcSize(lRow\CHUNK_SIZE))重新定义为UcsRowChunk
ElseIf UBound(mu uRowChunks)
Option Explicit
DefObj A-Z
Private Declare Function ArrPtr Lib "msvbvm60" Alias "VarPtr" (Ptr() As Any) As Long
Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (dst As Any, src As Any, ByVal nBytes As Long)
Private Const CHUNK_SIZE As Long = 100
Private Type UcsColChunk
ColValue() As Double
End Type
Private Type UcsRowValue
ColChunk() As UcsColChunk
End Type
Private Type UcsRowChunk
RowValue() As UcsRowValue
End Type
Private m_uRowChunks() As UcsRowChunk
Property Get Cell(ByVal lRow As Long, ByVal lCol As Long) As Double
On Error Resume Next
Cell = m_uRowChunks(lRow \ CHUNK_SIZE).RowValue(lRow Mod CHUNK_SIZE).ColChunk(lCol \ CHUNK_SIZE).ColValue(lCol Mod CHUNK_SIZE)
End Property
Property Let Cell(ByVal lRow As Long, ByVal lCol As Long, ByVal dblValue As Double)
If pvPeek(ArrPtr(m_uRowChunks)) = 0 Then
ReDim m_uRowChunks(0 To pvCalcSize(lRow \ CHUNK_SIZE)) As UcsRowChunk
ElseIf UBound(m_uRowChunks) < lRow \ CHUNK_SIZE Then
ReDim Preserve m_uRowChunks(0 To pvCalcSize(lRow \ CHUNK_SIZE)) As UcsRowChunk
End If
With m_uRowChunks(lRow \ CHUNK_SIZE)
If pvPeek(ArrPtr(.RowValue)) = 0 Then
ReDim .RowValue(0 To CHUNK_SIZE - 1) As UcsRowValue
End If
With .RowValue(lRow Mod CHUNK_SIZE)
If pvPeek(ArrPtr(.ColChunk)) = 0 Then
ReDim .ColChunk(0 To pvCalcSize(lCol \ CHUNK_SIZE)) As UcsColChunk
ElseIf UBound(.ColChunk) < lCol \ CHUNK_SIZE Then
ReDim Preserve .ColChunk(0 To pvCalcSize(lCol \ CHUNK_SIZE)) As UcsColChunk
End If
With .ColChunk(lCol \ CHUNK_SIZE)
If pvPeek(ArrPtr(.ColValue)) = 0 Then
ReDim .ColValue(0 To CHUNK_SIZE - 1) As Double
End If
.ColValue(lCol Mod CHUNK_SIZE) = dblValue
End With
End With
End With
End Property
Private Function pvCalcSize(ByVal lSize As Long) As Long
pvCalcSize = 2 ^ (Int(Log(lSize + 1) / Log(2)) + 1) - 1
End Function
Private Function pvPeek(ByVal lPtr As Long) As Long
Call CopyMemory(pvPeek, ByVal lPtr, 4)
End Function