int _CMDnetErosion(DBObjData *netData, DBObjData *inData, DBObjData *weightData, DBObjData *outData, DBFloat coeff, DBInt areaMult) { DBInt ret = DBSuccess, layerID, cellID, progress, maxProgress; DBFloat inValue, weight, outValue, *sumWeights; DBPosition pos; DBNetworkIF *netIF = new DBNetworkIF(netData); DBGridIF *inIF = new DBGridIF(inData); DBGridIF *outIF = new DBGridIF(outData); DBGridIF *weightIF = weightData != (DBObjData *) NULL ? new DBGridIF(weightData) : (DBGridIF *) NULL; DBObjRecord *inLayerRec, *outLayerRec, *weightLayerRec, *cellRec, *toCell; if ((sumWeights = (DBFloat *) calloc(netIF->CellNum(), sizeof(DBFloat))) == (DBFloat *) NULL) { CMmsgPrint(CMmsgSysError, "Memory allocation error in: %s %d", __FILE__, __LINE__); ret = DBFault; goto Stop; } layerID = 0; inLayerRec = inIF->Layer(layerID); outLayerRec = outIF->Layer(layerID); outIF->RenameLayer(outLayerRec, inLayerRec->Name()); outValue = outIF->MissingValue(outLayerRec); for (pos.Row = 0; pos.Row < outIF->RowNum(); pos.Row++) for (pos.Col = 0; pos.Col < outIF->ColNum(); pos.Col++) outIF->Value(outLayerRec, pos, outValue); for (layerID = 1; layerID < inIF->LayerNum(); ++layerID) { inLayerRec = inIF->Layer(layerID); if ((outLayerRec = outIF->AddLayer(inLayerRec->Name())) == (DBObjRecord *) NULL) { ret = DBFault; goto Stop; } for (pos.Row = 0; pos.Row < outIF->RowNum(); pos.Row++) for (pos.Col = 0; pos.Col < outIF->ColNum(); pos.Col++) outIF->Value(outLayerRec, pos, outValue); } maxProgress = inIF->LayerNum() * netIF->CellNum(); for (layerID = 0; layerID < inIF->LayerNum(); ++layerID) { inLayerRec = inIF->Layer(layerID); outLayerRec = outIF->Layer(layerID); if (weightIF != (DBGridIF *) NULL) weightLayerRec = weightIF->Layer(layerID % weightIF->LayerNum()); for (cellID = 0; cellID < netIF->CellNum(); cellID++) { sumWeights[cellID] = 0.0; cellRec = netIF->Cell(cellID); if (inIF->Value(inLayerRec, netIF->Center(cellRec), &inValue) == false) outIF->Value(outLayerRec, netIF->CellPosition(cellRec), 0.0); else { if (weightIF != (DBGridIF *) NULL) weight = weightIF->Value(weightLayerRec, netIF->Center(cellRec), &weight) == false ? 0.0 : weight * coeff; else weight = coeff; if (areaMult) weight = weight * netIF->CellArea(cellRec); sumWeights[cellID] = weight; outIF->Value(outLayerRec, netIF->CellPosition(cellRec), inValue * weight); } } for (cellID = netIF->CellNum() - 1; cellID >= 0; --cellID) { progress = layerID * netIF->CellNum() + (netIF->CellNum() - cellID); if (DBPause(progress * 100 / maxProgress)) goto Stop; cellRec = netIF->Cell(cellID); if ((toCell = netIF->ToCell(cellRec)) == (DBObjRecord *) NULL) continue; if (outIF->Value(outLayerRec, netIF->CellPosition(cellRec), &inValue) == false) continue; if (outIF->Value(outLayerRec, netIF->CellPosition(toCell), &outValue) == false) continue; sumWeights[toCell->RowID()] = sumWeights[toCell->RowID()] + weight; outIF->Value(outLayerRec, netIF->CellPosition(toCell), outValue + inValue); } outIF->RecalcStats(outLayerRec); } free(sumWeights); Stop: delete netIF; delete inIF; delete outIF; if (weightIF != (DBGridIF *) NULL) delete weightIF; return (ret); }
DBObjData *Compute(char *title, CMthreadUserExecFunc userFunc) { DBInt i, layerID, dataLayerID; size_t threadId; DBPosition pos; DBCoordinate coord; char *layerName; DBObjData *data; DBObjRecord *record; size_t threadsNum = CMthreadProcessorNum(); CMthreadTeam_t team; CMthreadJob_p job = (CMthreadJob_p) NULL; if (CMthreadTeamInitialize(&team, threadsNum) == (CMthreadTeam_p) NULL) { CMmsgPrint (CMmsgUsrError,"Team initialization error %s, %d",__FILE__,__LINE__); return ((DBObjData *) NULL); } if ((data = DBGridCreate(title, Extent, CellSize)) == (DBObjData *) NULL) return ((DBObjData *) NULL); data->Projection(GrdVar[0]->Projection()); // Taking projection from first grid variable GridIF = new DBGridIF(data); if (team.ThreadNum > 0) { if ((job = CMthreadJobCreate(GridIF->RowNum() * GridIF->ColNum(), userFunc, (void *) this)) == (CMthreadJob_p) NULL) { CMmsgPrint(CMmsgAppError, "Job creation error in %s:%d", __FILE__, __LINE__); CMthreadTeamDestroy(&team); return ((DBObjData *) NULL); } for (threadId = 0; threadId < team.ThreadNum; ++threadId) if (Table->Add("TEMPRecord") == (DBObjRecord *) NULL) { CMthreadTeamDestroy(&team); return ((DBObjData *) NULL); } } else { if ((record = Table->Add("TEMPRecord")) == (DBObjRecord *) NULL) return ((DBObjData *) NULL); } for (layerID = 0; layerID < LayerNum; ++layerID) { layerName = GrdVar[MasterVar]->CurrentLayer(layerID); for (i = 0; i < (DBInt) VarNum; ++i) { if ((dataLayerID = GrdVar[i]->FindLayer(layerName)) != DBFault) GrdVar[i]->CurrentLayer(dataLayerID); else { if (GrdVar[i]->LayerIsDated(0)) continue; GrdVar[i]->CurrentLayer(dataLayerID); } } if (layerID > 0) GridIF->AddLayer((char *) "New Layer"); LayerRec = GridIF->Layer(layerID); GridIF->RenameLayer(LayerRec, layerName); if (job != (CMthreadJob_p) NULL) CMthreadJobExecute(&team, job); else for (pos.Row = 0; pos.Row < GridIF->RowNum(); ++pos.Row) for (pos.Col = 0; pos.Col < GridIF->ColNum(); ++pos.Col) { GridIF->Pos2Coord(pos, coord); for (i = 0; i < (DBInt) VarNum; ++i) GrdVar[i]->GetVariable(record, coord); for (i = 0; i < (DBInt) ExpNum; ++i) Expressions[i]->Evaluate(record); GridIF->Value(LayerRec, pos, Operand->Float(record)); } GridIF->RecalcStats(LayerRec); } delete GridIF; CMthreadTeamDestroy(&team); return (data); }
DBInt RGlibDataStream2RGIS(DBObjData *outData, DBObjData *tmplData, FILE *inFile) { DBInt layerID = 0, itemSize; DBPosition pos; DBFloat val; void *data = (void *) NULL; MFVarHeader_t header; DBObjRecord *record; switch (tmplData->Type()) { case DBTypeVectorPoint: { DBInt itemID; DBDate date; DBObjTable *itemTable = outData->Table(DBrNItems); DBObjTableField *idField = new DBObjTableField("ItemID", DBTableFieldInt, "%6d", sizeof(DBInt), false); DBObjTableField *dateField = new DBObjTableField("Date", DBTableFieldDate, "%s", sizeof(DBDate), false); DBObjTableField *valField; DBVPointIF *pntIF = new DBVPointIF(tmplData); itemTable->AddField(idField); itemTable->AddField(dateField); while (MFVarReadHeader(&header, inFile)) { if (header.ItemNum != pntIF->ItemNum()) { CMmsgPrint(CMmsgUsrError, "Error: Datastream inconsistency %d %d!", header.ItemNum, pntIF->ItemNum()); return (DBFault); } if (data == (void *) NULL) { itemSize = MFVarItemSize(header.DataType); if ((data = (void *) realloc(data, header.ItemNum * itemSize)) == (void *) NULL) { CMmsgPrint(CMmsgSysError, "Memory allocation error in: %s %d", __FILE__, __LINE__); return (DBFault); } switch (header.DataType) { case MFByte: valField = new DBObjTableField("Value", DBTableFieldInt, "%2d", sizeof(char), false); case MFShort: valField = new DBObjTableField("Value", DBTableFieldInt, "%4d", sizeof(DBShort), false); case MFInt: valField = new DBObjTableField("Value", DBTableFieldInt, "%8d", sizeof(DBInt), false); case MFFloat: valField = new DBObjTableField("Value", DBTableFieldFloat, "%8.2f", sizeof(DBFloat4), false); case MFDouble: valField = new DBObjTableField("Value", DBTableFieldFloat, "%8.2f", sizeof(DBFloat), false); } itemTable->AddField(valField); } if ((int) fread(data, itemSize, header.ItemNum, inFile) != header.ItemNum) { CMmsgPrint(CMmsgSysError, "Error: Data stream read in: %s %d", __FILE__, __LINE__); return (DBFault); } for (itemID = 0; itemID < header.ItemNum; ++itemID) { record = itemTable->Add(header.Date); date.Set(header.Date); idField->Int(record, itemID); dateField->Date(record, date); /* decDateField->Float (record,date); */ switch (header.DataType) { case MFByte: valField->Int(record, ((char *) data)[itemID]); break; case MFShort: valField->Int(record, ((short *) data)[itemID]); break; case MFInt: valField->Int(record, ((int *) data)[itemID]); break; case MFFloat: valField->Float(record, ((float *) data)[itemID]); break; case MFDouble: valField->Float(record, ((double *) data)[itemID]); break; } } } delete pntIF; } break; case DBTypeGridContinuous: case DBTypeGridDiscrete: { DBGridIF *gridIF = new DBGridIF(outData); while (MFVarReadHeader(&header, inFile)) { if (header.ItemNum != gridIF->RowNum() * gridIF->ColNum()) { CMmsgPrint(CMmsgUsrError, "Error: Datastream inconsistency!"); return (DBFault); } if (layerID == 0) { itemSize = MFVarItemSize(header.DataType); if ((data = (void *) realloc(data, header.ItemNum * itemSize)) == (void *) NULL) { CMmsgPrint(CMmsgSysError, "Memory allocation error in: %s %d", __FILE__, __LINE__); return (DBFault); } record = gridIF->Layer(layerID); gridIF->RenameLayer(header.Date); } else record = gridIF->AddLayer(header.Date); switch (header.DataType) { case MFByte: case MFShort: case MFInt: gridIF->MissingValue(record, header.Missing.Int); break; case MFFloat: case MFDouble: gridIF->MissingValue(record, header.Missing.Float); break; } if ((int) fread(data, itemSize, header.ItemNum, inFile) != header.ItemNum) { CMmsgPrint(CMmsgSysError, "Error: Data stream read in: %s %d", __FILE__, __LINE__); return (DBFault); } for (pos.Row = 0; pos.Row < gridIF->RowNum(); ++pos.Row) for (pos.Col = 0; pos.Col < gridIF->ColNum(); ++pos.Col) { switch (header.DataType) { case MFByte: val = (DBFloat) (((char *) data)[pos.Row * gridIF->ColNum() + pos.Col]); break; case MFShort: val = (DBFloat) (((short *) data)[pos.Row * gridIF->ColNum() + pos.Col]); break; case MFInt: val = (DBFloat) (((int *) data)[pos.Row * gridIF->ColNum() + pos.Col]); break; case MFFloat: val = (DBFloat) (((float *) data)[pos.Row * gridIF->ColNum() + pos.Col]); break; case MFDouble: val = (DBFloat) (((double *) data)[pos.Row * gridIF->ColNum() + pos.Col]); break; } gridIF->Value(record, pos, val); } layerID++; } gridIF->RecalcStats(); } break; case DBTypeNetwork: { DBInt cellID; DBGridIF *gridIF = new DBGridIF(outData); DBNetworkIF *netIF = new DBNetworkIF(tmplData); while (MFVarReadHeader(&header, inFile)) { if (header.ItemNum != netIF->CellNum()) { CMmsgPrint(CMmsgUsrError, "Error: Datastream inconsistency!"); return (DBFault); } if (layerID == 0) { itemSize = MFVarItemSize(header.DataType); if ((data = (void *) realloc(data, header.ItemNum * itemSize)) == (void *) NULL) { CMmsgPrint(CMmsgSysError, "Memory allocation error in: %s %d", __FILE__, __LINE__); return (DBFault); } record = gridIF->Layer(layerID); gridIF->RenameLayer(header.Date); } else record = gridIF->AddLayer(header.Date); if ((int) fread(data, itemSize, header.ItemNum, inFile) != header.ItemNum) { CMmsgPrint(CMmsgSysError, "Error: Data stream read in: %s %d", __FILE__, __LINE__); delete netIF; return (DBFault); } for (pos.Row = 0; pos.Row < gridIF->RowNum(); ++pos.Row) for (pos.Col = 0; pos.Col < gridIF->ColNum(); ++pos.Col) gridIF->Value(record, pos, gridIF->MissingValue()); for (cellID = 0; cellID < netIF->CellNum(); ++cellID) { pos = netIF->CellPosition(netIF->Cell(cellID)); switch (header.DataType) { case MFByte: val = (DBFloat) (((char *) data)[cellID]); break; case MFShort: val = (DBFloat) (((short *) data)[cellID]); break; case MFInt: val = (DBFloat) (((int *) data)[cellID]); break; case MFFloat: val = (DBFloat) (((float *) data)[cellID]); break; case MFDouble: val = (DBFloat) (((double *) data)[cellID]); break; } gridIF->Value(record, pos, val); } layerID++; } gridIF->RecalcStats(); } break; } return (DBSuccess); }
int _CMDnetTransfer(DBObjData *netData, DBObjData *inData, DBObjData *weightData, DBObjData *outData, DBFloat coeff, DBObjData *coeffData, DBObjData *QData, DBObjData *HLData, DBFloat umax, DBFloat ksat, DBInt areaMult) { DBInt ret = DBSuccess, layerID, cellID, progress, maxProgress; DBFloat inValue, weight, outValue, *sumWeights, kCoeff, q, hl, Conc, Uptake, Vf; DBPosition pos; DBNetworkIF *netIF = new DBNetworkIF(netData); DBGridIF *inIF = new DBGridIF(inData); DBGridIF *outIF = new DBGridIF(outData); DBGridIF *weightIF = weightData != (DBObjData *) NULL ? new DBGridIF(weightData) : (DBGridIF *) NULL; DBGridIF *coeffIF = coeffData != (DBObjData *) NULL ? new DBGridIF(coeffData) : (DBGridIF *) NULL; DBGridIF *Q_IF = QData != (DBObjData *) NULL ? new DBGridIF(QData) : (DBGridIF *) NULL; DBGridIF *HL_IF = HLData != (DBObjData *) NULL ? new DBGridIF(HLData) : (DBGridIF *) NULL; DBObjRecord *inLayerRec, *outLayerRec, *weightLayerRec, *coeffLayerRec, *Q_LayerRec, *HL_LayerRec, *cellRec, *toCell; DBCoordinate coord; if ((sumWeights = (DBFloat *) calloc(netIF->CellNum(), sizeof(DBFloat))) == (DBFloat *) NULL) { CMmsgPrint(CMmsgSysError, "Memory allocation error in: %s %d", __FILE__, __LINE__); ret = DBFault; goto Stop; } layerID = 0; inLayerRec = inIF->Layer(layerID); outLayerRec = outIF->Layer(layerID); outIF->RenameLayer(outLayerRec, inLayerRec->Name()); outValue = outIF->MissingValue(outLayerRec); for (pos.Row = 0; pos.Row < outIF->RowNum(); pos.Row++) for (pos.Col = 0; pos.Col < outIF->ColNum(); pos.Col++) outIF->Value(outLayerRec, pos, outValue); for (layerID = 1; layerID < inIF->LayerNum(); ++layerID) { inLayerRec = inIF->Layer(layerID); if ((outLayerRec = outIF->AddLayer(inLayerRec->Name())) == (DBObjRecord *) NULL) { ret = DBFault; goto Stop; } for (pos.Row = 0; pos.Row < outIF->RowNum(); pos.Row++) for (pos.Col = 0; pos.Col < outIF->ColNum(); pos.Col++) outIF->Value(outLayerRec, pos, outValue); } maxProgress = inIF->LayerNum() * netIF->CellNum(); for (layerID = 0; layerID < inIF->LayerNum(); ++layerID) { inLayerRec = inIF->Layer(layerID); outLayerRec = outIF->Layer(layerID); if (weightIF != (DBGridIF *) NULL) weightLayerRec = weightIF->Layer(layerID % weightIF->LayerNum()); if (coeffIF != (DBGridIF *) NULL) coeffLayerRec = coeffIF->Layer(layerID % coeffIF->LayerNum()); if (Q_IF != (DBGridIF *) NULL) Q_LayerRec = Q_IF->Layer(layerID % Q_IF->LayerNum()); if (HL_IF != (DBGridIF *) NULL) HL_LayerRec = HL_IF->Layer(layerID % HL_IF->LayerNum()); for (cellID = 0; cellID < netIF->CellNum(); cellID++) { sumWeights[cellID] = 0.0; cellRec = netIF->Cell(cellID); coord = netIF->Center(cellRec); if (inIF->Value(inLayerRec, coord, &inValue) == false) outIF->Value(outLayerRec, netIF->CellPosition(cellRec), 0.0); else { if (weightIF != (DBGridIF *) NULL) weight = weightIF->Value(weightLayerRec, coord, &weight) == false ? 0.0 : weight * coeff; else weight = coeff; if (areaMult) weight = weight * netIF->CellArea(cellRec); sumWeights[cellID] = weight; outIF->Value(outLayerRec, netIF->CellPosition(cellRec), inValue * weight); } } for (cellID = netIF->CellNum() - 1; cellID >= 0; --cellID) { progress = layerID * netIF->CellNum() + (netIF->CellNum() - cellID); if (DBPause(progress * 100 / maxProgress)) goto Stop; cellRec = netIF->Cell(cellID); coord = netIF->Center(cellRec); if ((toCell = netIF->ToCell(cellRec)) == (DBObjRecord *) NULL) continue; if (outIF->Value(outLayerRec, netIF->CellPosition(cellRec), &inValue) == false) continue; if (outIF->Value(outLayerRec, netIF->CellPosition(toCell), &outValue) == false) continue; sumWeights[toCell->RowID()] = sumWeights[toCell->RowID()] + weight; if (coeffIF != (DBGridIF *) NULL) { if (coeffIF->Value(coeffLayerRec, netIF->Center(cellRec), &kCoeff) == false) kCoeff = 1.0; } else { if (((Q_IF == (DBGridIF *) NULL) || (Q_IF->Value(Q_LayerRec, netIF->Center(cellRec), &q) == false)) || ((HL_IF == (DBGridIF *) NULL) || (HL_IF->Value(HL_LayerRec, netIF->Center(cellRec), &hl) == false)) || (umax == 0) || (ksat == 0)) kCoeff = 1.0; else { if ((q > 0) && (hl > 0)) { Conc = ((inValue / (q * 86400 * 365)) * 1000 * 1000); /* mg/m3 - assume input = kg/yr, Q is m3/s convert to m3/yr kg to mg */ Uptake = (umax * 24 * 365 * Conc) / (ksat * 1000 + Conc); /* mg/m2/yr - umax and ksat/Conc are in mg/m2/hr, mg/m3 */ if (Uptake > 0) { Vf = Uptake / Conc; /* Vf in m/yr */ } else Vf = 0; kCoeff = pow(2.71828, (-1.0 * Vf / hl)); /* HL in m/yr */ /* if ((cellID == 5390) || (cellID == 5015) || (cellID == 4905) || (cellID == 4857)) printf("%i, %f, %f, %f, %f, %f, %f, %f, %f, %f, %f \n", cellID, outValue, inValue, q, hl, umax, ksat, Conc, Uptake, Vf, kCoeff); */ } else kCoeff = 0; } } /* if ((cellID == 5390) || (cellID == 5015) || (cellID == 4905) || (cellID == 4857)) printf("%i, %f \n", cellID, inValue); */ inValue = kCoeff * inValue; outIF->Value(outLayerRec, netIF->CellPosition(toCell), outValue + inValue); } outIF->RecalcStats(outLayerRec); } free(sumWeights); Stop: delete netIF; delete inIF; delete outIF; if (weightIF != (DBGridIF *) NULL) delete weightIF; return (ret); return (DBSuccess); }