asp classic - quien - crítica del código: ¿estoy creando una máquina Rube Goldberg?
rube goldberg quien es (3)
No hay nada de malo en hacerlo a tu manera. Las bibliotecas ADO no estaban realmente tan bien diseñadas, y usarlas directamente requiere demasiadas líneas de código, por lo que siempre tengo algunas funciones de utilidad que hacen que sea más fácil hacer cosas en común. Por ejemplo, es muy útil crear una función "ExecuteScalar" que ejecute SQL que devuelve exactamente un valor, para todos aquellos SELECT COUNT (*) que pueda hacer.
PERO - su función myPush
es extremadamente ineficiente. ReDim Preserve
toma mucho tiempo porque tiene que reasignar la memoria y copiar todo. Esto resulta en el rendimiento O (n 2 ), o lo que yo llamo un algoritmo Shlemiel the Painter . La mejor práctica recomendada sería comenzar por atenuar, por ejemplo, una matriz con espacio para 16 valores, y duplicar su tamaño cada vez que la llene. De esta forma, no tendrá que llamar a ReDim Preserve
más de Lg 2 n veces.
Estoy haciendo una buena cantidad de llamadas a las tablas de la base de datos a través de ADO. Con el ánimo de mantener las cosas SECAS, escribí las siguientes funciones para devolver una matriz de valores de un juego de registros. ¿Es esta liebre cerebral? Lo uso principalmente para capturar un conjunto de valores de cuadro combinado y similares, nunca para valores enormes. Ejemplo de uso (manejo de errores eliminado por brevedad):
Function getEmployeeList()
getEmployeeList= Array()
strSQL = "SELECT emp_id, emp_name from employees"
getEmployeeList = getSQLArray( strSQL, "|" )
End Function
Entonces solo hago lo que quiero con la matriz devuelta.
Function getSQLArray( SQL, delimiter )
''*************************************************************************************
'' Input a SQL statement and an optional delimiter, and this function
'' will return an array of strings delimited by whatever (pipe defaults)
'' You can perform a Split to extract the appropriate values.
'' Additionally, this function will return error messages as well; check for
'' a return of error & delimiter & errNum & delimiter & errDescription
''*************************************************************************************
getSQLArray = Array()
Err.Number = 0
Set objCon = Server.CreateObject("ADODB.Connection")
objCon.Open oracleDSN
Set objRS = objCon.Execute(SQL)
if objRS.BOF = false and objRS.EOF = false then
Do While Not objRS.EOF
for fieldIndex=0 to (objRS.Fields.Count - 1)
If ( fieldIndex <> 0 ) Then
fieldValue = testEmpty(objRS.Fields.Item(fieldIndex))
recordString = recordString & delimiter & fieldValue
Else
recordString = CStr(objRS.Fields.Item(fieldIndex))
End If
Next
Call myPush( recordString, getSQLArray )
objRS.MoveNext
Loop
End If
Set objRS = Nothing
objCon.Close
Set objCon = Nothing
End Function
Sub myPush(newElement, inputArray)
Dim i
i = UBound(inputArray) + 1
ReDim Preserve inputArray(i)
inputArray(i) = newElement
End Sub
Function testEmpty( inputValue )
If (trim( inputValue ) = "") OR (IsNull( inputValue )) Then
testEmpty = ""
Else
testEmpty = inputValue
End If
End Function
Las preguntas que tengo son: ¿Tiene sentido abstraer toda la creación / apertura / manejo de errores del conjunto de registros en su propia llamada a funciones como esta? ¿Estoy construyendo una máquina Rube Goldberg, donde cualquier persona que mantenga este código maldecirá mi nombre?
¿Debo aspirar y escribir algunas macros para escupir el código de conexión ADO, en lugar de intentar hacerlo en una función?
Soy muy nuevo en ASP, por lo que tengo agujeros en sus capacidades / mejores prácticas, por lo que cualquier aportación será apreciada.
Sí, tiene sentido factorizar tareas comunes. No veo nada malo con la idea general. Me pregunto por qué estás devolviendo una matriz de cadenas separadas por un delimitador; también podría devolver una matriz de matrices.
Me pregunto por qué no estás usando GetRows. Devuelve un conjunto, encontrará más detalles aquí: http://www.w3schools.com/ado/met_rs_getrows.asp
Algunas notas sobre GetRows:
Set objRS = Server.CreateObject ("ADODB.Recordset")
objRS.Open cmd, , adOpenForwardOnly, adLockReadOnly
If Not objRS.EOF Then
astrEmployees = objRS.GetRows()
intRecFirst = LBound(astrEmployees, 2)
intRecLast = UBound(astrEmployees, 2)
FirstField = 0
SecondField = 1
End If
''2nd field of the fourth row (record) ''
Response.Write (SecondField, 3)