protected bool CheckFactorAndResponseNotBlank(string factor, string response, string displayName) { if (String.IsNullOrEmpty(response) || String.IsNullOrEmpty(factor)) { return(true); } bool hasWarning = false; bool hasError = false; foreach (DataRow row in DataTable.Rows) { //Check that there are treatment levels for where there are response data if (!String.IsNullOrEmpty(row[response].ToString()) && String.IsNullOrEmpty(row[factor].ToString())) { hasError = true; break; } //check that the response contains data for each treatment (not fatal) if (String.IsNullOrEmpty(row[response].ToString()) && !String.IsNullOrEmpty(row[factor].ToString())) { hasWarning = true; } } if (hasError) { validationInfo.AddErrorMessage("The " + displayName + " (" + factor + ") contains missing data where there are observations present in the Response. Please check the input data and make sure the data was entered correctly."); return(false); } else if (hasWarning) { string message = "The Response (" + response + ") contains missing data. Any rows of the dataset that contain missing responses will be excluded prior to the analysis."; validationInfo.AddWarningMessage(message); } return(true); }
public override ValidationInfo Validate() { string[] pValues = pvVariables.PValues.Replace(" ", "").Split(','); //split list by comma if (pValues.Any(x => x == "<0.001")) { ValidationInfo.AddWarningMessage("You have entered unadjusted p-value(s) of the form <0.001. For the purposes of the numerical calculations this value has been replaced with 0.00099 and hence the adjusted p-values may be unduly conservative."); } if (pValues.Any(x => x == "<0.0001")) { ValidationInfo.AddWarningMessage("You have entered unadjusted p-value(s) of the form <0.0001. For the purposes of the numerical calculations this value has been replaced with 0.000099 and hence the adjusted p-values may be unduly conservative."); } //if get here then no errors so return true return(ValidationInfo); }
public override ValidationInfo Validate() { //go through all the column names, if any are numeric then stop the analysis List <string> allVars = new List <string>(); allVars.Add(npVariables.Treatment); allVars.Add(npVariables.Response); allVars.Add(npVariables.OtherDesignFactor); if (!CheckColumnNames(allVars)) { return(ValidationInfo); } if (!CheckIsNumeric(npVariables.Response)) { ValidationInfo.AddErrorMessage("The Response (" + npVariables.Response + ") contains non-numeric data that cannot be processed. Please check the input data and make sure the data was entered correctly."); return(ValidationInfo); } if (!CheckFactorsHaveLevels(npVariables.Treatment)) { return(ValidationInfo); } if (!CheckResponsesPerLevel(npVariables.Treatment, npVariables.Response, ReflectionExtensions.GetPropertyDisplayName <NonParametricAnalysisModel>(i => i.Treatment))) { return(ValidationInfo); } //check response and treatments contain values if (!CheckFactorAndResponseNotBlank(npVariables.Treatment, npVariables.Response, ReflectionExtensions.GetPropertyDisplayName <NonParametricAnalysisModel>(i => i.Treatment))) { return(ValidationInfo); } //if only two levels and all treats or to control selected, then need to only do KW if (CountDistinctLevels(npVariables.Treatment) == 2 && String.IsNullOrEmpty(npVariables.OtherDesignFactor) && npVariables.AnalysisType != NonParametricAnalysisModel.AnalysisOption.MannWhitney) { string message = "The Treatment factor (" + npVariables.Treatment + ") has only two levels so a Mann-Whitney test will be presented."; ValidationInfo.AddWarningMessage(message); } //if get here then no errors so return true return(ValidationInfo); }
public override ValidationInfo Validate() { //go through all the column names, if any are numeric then stop the analysis List <string> allVars = new List <string>(); allVars.Add(csfetVariables.Response); allVars.Add(csfetVariables.GroupingFactor); allVars.Add(csfetVariables.ResponseCategories); if (!CheckColumnNames(allVars)) { return(ValidationInfo); } if (!CheckIsNumeric(csfetVariables.Response)) { ValidationInfo.AddErrorMessage("The Response (" + csfetVariables.Response + ") contains non-numeric data that cannot be processed. Please check the input data and make sure the data was entered correctly."); return(ValidationInfo); } if (!CheckFactorAndResponseNotBlank(csfetVariables.GroupingFactor, csfetVariables.Response, ReflectionExtensions.GetPropertyDisplayName <ChiSquaredAndFishersExactTestModel>(i => i.GroupingFactor))) { return(ValidationInfo); } if (!CheckFactorAndResponseNotBlank(csfetVariables.ResponseCategories, csfetVariables.Response, ReflectionExtensions.GetPropertyDisplayName <ChiSquaredAndFishersExactTestModel>(i => i.ResponseCategories, true))) { return(ValidationInfo); } if (csfetVariables.BarnardsTest && (GetLevels(csfetVariables.GroupingFactor).Count() > 2 || GetLevels(csfetVariables.ResponseCategories).Count() > 2)) { ValidationInfo.AddWarningMessage("Grouping factor or the Response categories have more than two levels. Barnard's test can only be performed when there are two levels of the Grouping factor and two Response categories."); } //if get here then no errors so return true return(ValidationInfo); }
private bool CategoricalAgainstContinuousVariableChecks(List <string> categorical, string continuous) { foreach (string catFactor in categorical) //go through each categorical factor and do the check on each { string factorType; if (ndaVariables.Treatments.Contains(catFactor)) { factorType = ReflectionExtensions.GetPropertyDisplayName <SingleMeasuresParametricAnalysisModel>(i => i.Treatments); } else { factorType = ReflectionExtensions.GetPropertyDisplayName <SingleMeasuresParametricAnalysisModel>(i => i.OtherDesignFactors); } string responseType; if (ndaVariables.Response.Contains(continuous)) { responseType = ReflectionExtensions.GetPropertyDisplayName <SingleMeasuresParametricAnalysisModel>(i => i.Response); } else { responseType = ReflectionExtensions.GetPropertyDisplayName <SingleMeasuresParametricAnalysisModel>(i => i.Covariates); } //Now that the whole column checks have been done, ensure that the treatment and response for each row is ok List <string> categoricalRow = new List <string>(); List <string> continuousRow = new List <string>(); foreach (DataRow row in DataTable.Rows) //assemble a list of the categorical data and the continuous data... { categoricalRow.Add(row[catFactor].ToString()); continuousRow.Add(row[continuous].ToString()); } for (int i = 0; i < DataTable.Rows.Count; i++) //use for loop cos its easier to compare the indexes of the cat and cont rows { //Check that the "response" does not contains non-numeric data bool parsedOK = Double.TryParse(continuousRow[i], out double parsedValue); if (!String.IsNullOrEmpty(continuousRow[i]) && !parsedOK) { ValidationInfo.AddErrorMessage("The " + responseType + " (" + ndaVariables.Response + ") contains non-numerical data which cannot be processed. Please check the input data and make sure the data was entered correctly."); return(false); } //Check that there are no responses where the treatments are blank if (String.IsNullOrEmpty(categoricalRow[i]) && !String.IsNullOrEmpty(continuousRow[i])) { ValidationInfo.AddErrorMessage("The " + factorType + " (" + catFactor + ") contains missing data where there are observations present in the " + responseType + ". Please check the input data and make sure the data was entered correctly."); return(false); } //check that the "response" contains data for each "treatment" (not fatal) if (!String.IsNullOrEmpty(categoricalRow[i]) && String.IsNullOrEmpty(continuousRow[i])) { string mess = "The " + responseType + " contains missing data."; if (responseType == "covariate") { mess = mess + Environment.NewLine + " Any response that does not have a corresponding covariate will be excluded from the analysis."; } ValidationInfo.AddWarningMessage(mess); } } } //if got here then all checks ok, return true return(true); }
public override ValidationInfo Validate() { //go through all the column names, if any are numeric then stop the analysis List <string> allVars = new List <string>(); allVars.Add(drnlrVariables.Response); allVars.Add(drnlrVariables.Dose); allVars.Add(drnlrVariables.QCResponse); allVars.Add(drnlrVariables.QCDose); allVars.Add(drnlrVariables.SamplesResponse); allVars.Add(drnlrVariables.EquationYAxis); allVars.Add(drnlrVariables.EquationXAxis); if (!CheckColumnNames(allVars)) { return(ValidationInfo); } //Check that all the columns are numeric if (!CheckIsNumeric(drnlrVariables.Response)) { ValidationInfo.AddErrorMessage("The Response (" + drnlrVariables.Response + ") contains non-numeric data which cannot be processed. Please check the input data and make sure the data was entered correctly."); return(ValidationInfo); } if (!CheckIsNumeric(drnlrVariables.Dose)) { ValidationInfo.AddErrorMessage("The Dose (" + drnlrVariables.Dose + ") contains non-numeric data which cannot be processed. Please check the input data and make sure the data was entered correctly."); return(ValidationInfo); } if (!CheckIsNumeric(drnlrVariables.QCResponse)) { ValidationInfo.AddErrorMessage("The QC Response (" + drnlrVariables.QCResponse + ") contains non-numeric data which cannot be processed. Please check the input data and make sure the data was entered correctly."); return(ValidationInfo); } if (!CheckIsNumeric(drnlrVariables.QCDose)) { ValidationInfo.AddErrorMessage("The QC Dose (" + drnlrVariables.QCDose + ") contains non-numeric data which cannot be processed. Please check the input data and make sure the data was entered correctly."); return(ValidationInfo); } if (!CheckIsNumeric(drnlrVariables.SamplesResponse)) { ValidationInfo.AddErrorMessage("The Sample (" + drnlrVariables.SamplesResponse + ") contains non-numeric data which cannot be processed. Please check the input data and make sure the data was entered correctly."); return(ValidationInfo); } //check that there is more than one value in the response variables if (drnlrVariables.AnalysisType == DoseResponseAndNonLinearRegressionAnalysisModel.AnalysisOption.FourParameter) { if (CountResponses(drnlrVariables.Response) == 1) { ValidationInfo.AddErrorMessage("The Response (" + drnlrVariables.Response + ") contains only one value, please choose another response."); return(ValidationInfo); } if (!String.IsNullOrEmpty(drnlrVariables.QCResponse) && CountResponses(drnlrVariables.QCResponse) == 1) { ValidationInfo.AddErrorMessage("The QC Response (" + drnlrVariables.Response + ") contains only one value, please choose another QC response."); return(ValidationInfo); } //check response and doses contain values if (!CheckFactorAndResponseNotBlank(drnlrVariables.Dose, drnlrVariables.Response, ReflectionExtensions.GetPropertyDisplayName <DoseResponseAndNonLinearRegressionAnalysisModel>(i => i.Dose))) { return(ValidationInfo); } if (!CheckFactorAndResponseNotBlank(drnlrVariables.QCDose, drnlrVariables.QCResponse, ReflectionExtensions.GetPropertyDisplayName <DoseResponseAndNonLinearRegressionAnalysisModel>(i => i.QCDose))) { return(ValidationInfo); } int noFixedParameters = 0; if (drnlrVariables.MinCoeff.HasValue) { noFixedParameters++; } if (drnlrVariables.MaxCoeff.HasValue) { noFixedParameters++; } if (drnlrVariables.SlopeCoeff.HasValue) { noFixedParameters++; } if (drnlrVariables.EDICCoeff.HasValue) { noFixedParameters++; } int noOfLevels = CountDistinctLevels(drnlrVariables.Dose); if (noOfLevels == 4 && noFixedParameters < 1) { ValidationInfo.AddErrorMessage("As you only have measured responses at four doses you cannot fit the selected dose response curve. You will need to fix at least one of the parameters."); return(ValidationInfo); } else if (noOfLevels == 3 && noFixedParameters < 2) { ValidationInfo.AddErrorMessage("As you only have measured responses at three doses you cannot fit the selected dose response curve. You will need to fix at least two of the parameters."); return(ValidationInfo); } else if (noOfLevels == 2 && noFixedParameters < 3) { ValidationInfo.AddErrorMessage("As you only have measured responses at two doses you cannot fit the selected dose response curve. You will need to fix at least three of the parameters."); return(ValidationInfo); } else if (noOfLevels == 1 && noFixedParameters < 4) { ValidationInfo.AddErrorMessage("As you only have measured responses at one dose you cannot fit the selected dose response curve."); return(ValidationInfo); } //go through each row in the datatable and check transforms are ok CheckTransformations(drnlrVariables.ResponseTransformation, drnlrVariables.Response); CheckTransformations(drnlrVariables.ResponseTransformation, drnlrVariables.QCResponse); CheckTransformations(drnlrVariables.ResponseTransformation, drnlrVariables.SamplesResponse); //check that if fixed parameter is set then start value is not set, else add warning... bool warningForFixedAndStart = false; if (drnlrVariables.MinCoeff.HasValue && drnlrVariables.MinStartValue.HasValue) { warningForFixedAndStart = true; } else if (drnlrVariables.MaxCoeff.HasValue && drnlrVariables.MaxStartValue.HasValue) { warningForFixedAndStart = true; } else if (drnlrVariables.SlopeCoeff.HasValue && drnlrVariables.SlopeStartValue.HasValue) { warningForFixedAndStart = true; } else if (drnlrVariables.EDICCoeff.HasValue && drnlrVariables.EDICStartValue.HasValue) { warningForFixedAndStart = true; } if (warningForFixedAndStart) { ValidationInfo.AddWarningMessage("You have defined a start value for a parameter that has been fixed. The start value is ignored in the analysis."); } if (drnlrVariables.MinCoeff > drnlrVariables.MaxCoeff) { ValidationInfo.AddErrorMessage("The max coefficient is greater than the min coefficient."); return(ValidationInfo); } if (drnlrVariables.MinStartValue > drnlrVariables.MaxStartValue) { ValidationInfo.AddErrorMessage("The max start value is greater than the min start value."); return(ValidationInfo); } } else if (drnlrVariables.AnalysisType == DoseResponseAndNonLinearRegressionAnalysisModel.AnalysisOption.Equation && !drnlrVariables.Equation.Contains("x")) { ValidationInfo.AddErrorMessage("The formula should be of the form f=y(x) with x lower case."); return(ValidationInfo); } //if get here then no errors so return true return(ValidationInfo); }
public override ValidationInfo Validate() { //go through all the column names, if any are numeric then stop the analysis List <string> allVars = new List <string>(); allVars.AddVariables(rmVariables.Treatments); allVars.AddVariables(rmVariables.OtherDesignFactors); allVars.AddVariables(rmVariables.RepeatedFactor); allVars.AddVariables(rmVariables.Subject); allVars.AddVariables(rmVariables.Response); allVars.AddVariables(rmVariables.Covariates); if (!CheckColumnNames(allVars)) { return(ValidationInfo); } //Do checks to ensure that treatments contain a response etc and the responses contain a treatment etc... if (!CheckResponsesPerLevel(rmVariables.Treatments, rmVariables.Response, ReflectionExtensions.GetPropertyDisplayName <RepeatedMeasuresParametricAnalysisModel>(i => i.Treatments))) { return(ValidationInfo); } if (!CheckResponsesPerLevel(rmVariables.OtherDesignFactors, rmVariables.Response, ReflectionExtensions.GetPropertyDisplayName <RepeatedMeasuresParametricAnalysisModel>(i => i.OtherDesignFactors))) { return(ValidationInfo); } if (!CheckResponsesPerLevel(rmVariables.RepeatedFactor, rmVariables.Response, ReflectionExtensions.GetPropertyDisplayName <RepeatedMeasuresParametricAnalysisModel>(i => i.RepeatedFactor))) { return(ValidationInfo); } //Check that the number of responses for the subject is at least 1 Dictionary <string, int> levelResponses = ResponsesPerLevel(rmVariables.Subject, rmVariables.Response); foreach (KeyValuePair <string, int> level in levelResponses) { if (level.Value < 2) { ValidationInfo.AddWarningMessage("There is no replication in one or more of the levels of the Subject factor (" + rmVariables.Subject + "). This can lead to unreliable results so you may want to remove any subjects from the dataset with only one replicate."); break; } } //First create a list of categorical variables selected (i.e. as treatments and other factors) List <string> categorical = new List <string>(); categorical.AddVariables(rmVariables.Treatments); categorical.AddVariables(rmVariables.OtherDesignFactors); categorical.Add(rmVariables.RepeatedFactor); categorical.Add(rmVariables.Subject); //check that the factors have at least 2 levels if (!CheckFactorsHaveLevels(categorical, true)) { return(ValidationInfo); } //do data checks on the treatments/other factors and response if (!CategoricalAgainstContinuousVariableChecks(categorical, rmVariables.Response)) { return(ValidationInfo); } //check transformations CheckTransformations(rmVariables.ResponseTransformation, rmVariables.Response); if (rmVariables.Covariates != null) { CheckTransformations(rmVariables.CovariateTransformation, rmVariables.Covariates, true); } //do data checks on the treatments/other factors and covariate (if selected) if (rmVariables.Covariates != null) { foreach (string covariate in rmVariables.Covariates) { if (!CategoricalAgainstContinuousVariableChecks(categorical, covariate)) { return(ValidationInfo); } } } //Check that each subject is only present in one treatment factor if (!CheckSubjectIsPresentInOnlyOneFactor(rmVariables.Treatments, false)) { return(ValidationInfo); } //Check that each subject is only present in one blocking factor if (rmVariables.OtherDesignFactors != null && !CheckSubjectIsPresentInOnlyOneFactor(rmVariables.OtherDesignFactors, true)) { return(ValidationInfo); } //check that the replication of treatment factors in each timepoint is greater than 1 if (!CheckReplicationOfTreatmentFactors()) { return(ValidationInfo); } //Here we are checking that all treatment combinations are present at each time point in the design if (!CheckTreatmentCombinations()) { return(ValidationInfo); } //if get here then no errors so return true return(ValidationInfo); }
public override ValidationInfo Validate() { //first just check to ensure that the user has actually selected something to output! if (!gaVariables.ErrorBarPlotSelected && !gaVariables.BoxplotSelected && !gaVariables.CaseProfilesPlotSelected && !gaVariables.HistogramSelected && !gaVariables.ScatterplotSelected) { ValidationInfo.AddErrorMessage("You have not selected anything to output!"); return(ValidationInfo); } //go through all the column names, if any are numeric then stop the analysis List <string> allVars = new List <string>(); allVars.Add(gaVariables.XAxis); allVars.Add(gaVariables.Response); if (!CheckColumnNames(allVars)) { return(ValidationInfo); } //if the x-axis is selected then check if it is numeric bool xIsNumeric = false; if (!String.IsNullOrEmpty(gaVariables.XAxis)) { xIsNumeric = CheckIsNumeric(gaVariables.XAxis); //if the x-axis has been transformed then check that all is numeric if (!xIsNumeric && gaVariables.XAxisTransformation != "None") { ValidationInfo.AddWarningMessage("You have " + gaVariables.XAxisTransformation + " transformed the x-axis variable (" + gaVariables.XAxis + "). Unfortunately the x-axis variable is non-numerical and hence cannot be transformed. The transformation has been ignored."); } } //if the response is selected then check if it is numeric bool yIsNumeric = CheckIsNumeric(gaVariables.Response); //check that both axes are not numeric (or y is not numeric if histogram selected) if (!yIsNumeric && String.IsNullOrEmpty(gaVariables.XAxis) && gaVariables.HistogramSelected) { ValidationInfo.AddErrorMessage("As the Response is non-numeric, no histogram or other output has been produced."); return(ValidationInfo); } else if (!xIsNumeric && !yIsNumeric) { ValidationInfo.AddErrorMessage("The response variable is not numeric."); return(ValidationInfo); } if (!yIsNumeric && gaVariables.ResponseTransformation != "None") { ValidationInfo.AddWarningMessage("You have " + gaVariables.ResponseTransformation + " transformed the Response (" + gaVariables.Response + "). Unfortunately the Response is non-numerical and hence cannot be transformed. The transformation has been ignored."); } if (!yIsNumeric && !String.IsNullOrEmpty(gaVariables.Response) && (gaVariables.HistogramSelected || gaVariables.CaseProfilesPlotSelected || gaVariables.BoxplotSelected || gaVariables.ErrorBarPlotSelected)) { ValidationInfo.AddWarningMessage("Only the scatterplot option accepts non-numeric response variables. As the response is non-numeric, no plot other than a scatterplot can be produced."); } //check that the cat factors are numeric if (!String.IsNullOrEmpty(gaVariables.FirstCatFactor) && CheckIsNumeric(gaVariables.FirstCatFactor)) { ValidationInfo.AddWarningMessage("The 1st categorisation factor is numerical. Each numerical value present will consitute a category."); } if (!String.IsNullOrEmpty(gaVariables.SecondCatFactor) && CheckIsNumeric(gaVariables.SecondCatFactor)) { ValidationInfo.AddWarningMessage("The 2nd categorisation factor is numerical. Each numerical value present will consitute a category."); } //check that the cat factors have more than 1 level if (!String.IsNullOrEmpty(gaVariables.FirstCatFactor) && CountDistinctLevels(gaVariables.FirstCatFactor) == 1) { ValidationInfo.AddErrorMessage("The 1st categorisation factor has only one distinct level. Please review your selection."); return(ValidationInfo); } if (!String.IsNullOrEmpty(gaVariables.SecondCatFactor) && CountDistinctLevels(gaVariables.SecondCatFactor) == 1) { ValidationInfo.AddErrorMessage("The 2nd categorisation factor has only one distinct level. Please review your selection."); return(ValidationInfo); } //check if linear fit selected that both axes are numeric if ((!xIsNumeric || !yIsNumeric) && gaVariables.LinearFitSelected) { ValidationInfo.AddWarningMessage("As one of the axes is non-numeric, the best fit linear line is not included on the scatterplot."); } //check if SEM or boxplot selected that x is numeric if (xIsNumeric && (gaVariables.ErrorBarPlotSelected || gaVariables.BoxplotSelected)) { ValidationInfo.AddWarningMessage("The x-axis variable is numeric, for all plots other than scatterplot this will be treated as categorical."); } //check if the histogram is selected and the x-axis is blank if (gaVariables.HistogramSelected && !String.IsNullOrEmpty(gaVariables.XAxis)) { ValidationInfo.AddWarningMessage("The x-axis variable is ignored in the Histogram plot option. If you wish to include a categorisation factor in the plot, then select the categorisation factors."); } //go through each row in the datatable and do further checks... CheckTransformations(gaVariables.XAxisTransformation, gaVariables.XAxis); //if the response has been transformed check if the value is <= 0 CheckTransformations(gaVariables.ResponseTransformation, gaVariables.Response); foreach (DataRow row in DataTable.Rows) { //check that the x-axis has values for each response value if (!String.IsNullOrEmpty(gaVariables.XAxis)) { if (!String.IsNullOrEmpty(row[gaVariables.Response].ToString()) && String.IsNullOrEmpty(row[gaVariables.XAxis].ToString())) { ValidationInfo.AddWarningMessage("The x-axis variable (" + gaVariables.XAxis + ") contains missing values whereas the Response (" + gaVariables.Response + ") contains data, these responses will therefore be excluded from all analyses. To generate the Histogram containing these excluded responses (which does not require an x-axis variable) deselect the x-axis variable prior to analysis."); } else if (String.IsNullOrEmpty(row[gaVariables.Response].ToString()) && !String.IsNullOrEmpty(row[gaVariables.XAxis].ToString())) { ValidationInfo.AddWarningMessage("The Response (" + gaVariables.Response + ") contains missing values whereas the x-axis variable (" + gaVariables.XAxis + ") contains data. The corresponding x-axis variable values have been excluded from the analysis."); } } //check that the 1st cat factor has values for each response value if (!String.IsNullOrEmpty(gaVariables.FirstCatFactor)) { if (!String.IsNullOrEmpty(row[gaVariables.Response].ToString()) && String.IsNullOrEmpty(row[gaVariables.FirstCatFactor].ToString())) { ValidationInfo.AddErrorMessage("The 1st categorisation factor (" + gaVariables.FirstCatFactor + ") contains missing values whereas the Response (" + gaVariables.Response + ") contains data."); return(ValidationInfo); } else if (String.IsNullOrEmpty(row[gaVariables.Response].ToString()) && !String.IsNullOrEmpty(row[gaVariables.FirstCatFactor].ToString())) { ValidationInfo.AddWarningMessage("The Response (" + gaVariables.Response + ") contains missing values whereas the 1st categorisation factor (" + gaVariables.FirstCatFactor + ") contains data. The corresponding 1st categorisation factor values have been excluded from the analysis."); } } //check that the 2nd cat factor has values for each response value if (!String.IsNullOrEmpty(gaVariables.SecondCatFactor)) { if (!String.IsNullOrEmpty(row[gaVariables.Response].ToString()) && String.IsNullOrEmpty(row[gaVariables.SecondCatFactor].ToString())) { ValidationInfo.AddErrorMessage("The 2nd categorisation factor (" + gaVariables.SecondCatFactor + ") contains missing values whereas the Response (" + gaVariables.Response + ") contains data."); return(ValidationInfo); } else if (String.IsNullOrEmpty(row[gaVariables.Response].ToString()) && !String.IsNullOrEmpty(row[gaVariables.SecondCatFactor].ToString())) { ValidationInfo.AddWarningMessage("The Response (" + gaVariables.Response + ") contains missing values whereas the 2nd categorisation factor (" + gaVariables.SecondCatFactor + ") contains data. The corresponding 2nd categorisation factor values have been excluded from the analysis."); } } //check that the 1st cat factor has values for each x-axis value if (!String.IsNullOrEmpty(gaVariables.XAxis) && !String.IsNullOrEmpty(gaVariables.FirstCatFactor)) { if (!String.IsNullOrEmpty(row[gaVariables.XAxis].ToString()) && String.IsNullOrEmpty(row[gaVariables.FirstCatFactor].ToString())) { ValidationInfo.AddErrorMessage("The 1st categorisation factor (" + gaVariables.FirstCatFactor + ") contains missing values whereas the x-axis variable (" + gaVariables.XAxis + ") contains data."); return(ValidationInfo); } } //check that the 2nd cat factor has values for each x-axis value if (!String.IsNullOrEmpty(gaVariables.XAxis) && !String.IsNullOrEmpty(gaVariables.SecondCatFactor)) { if (!String.IsNullOrEmpty(row[gaVariables.XAxis].ToString()) && String.IsNullOrEmpty(row[gaVariables.SecondCatFactor].ToString())) { ValidationInfo.AddWarningMessage("The 2nd categorisation factor (" + gaVariables.SecondCatFactor + ") contains missing values whereas the x-axis variable (" + gaVariables.XAxis + ") contains data. The corresponding x-axis variable values have been excluded from the analysis."); } } } //check x axis levels ordering if (!CheckLevelsOrdering(gaVariables.XAxisLevelsOrder, gaVariables.XAxis, ReflectionExtensions.GetPropertyDisplayName <GraphicalAnalysisModel>(i => i.XAxisLevelsOrder), ReflectionExtensions.GetPropertyDisplayName <GraphicalAnalysisModel>(i => i.XAxis))) { return(ValidationInfo); } if (!CheckLevelsOrdering(gaVariables.FirstCatFactorLevelsOrder, gaVariables.FirstCatFactor, ReflectionExtensions.GetPropertyDisplayName <GraphicalAnalysisModel>(i => i.FirstCatFactorLevelsOrder), ReflectionExtensions.GetPropertyDisplayName <GraphicalAnalysisModel>(i => i.FirstCatFactor))) { return(ValidationInfo); } if (!CheckLevelsOrdering(gaVariables.SecondCatFactorLevelsOrder, gaVariables.SecondCatFactor, ReflectionExtensions.GetPropertyDisplayName <GraphicalAnalysisModel>(i => i.SecondCatFactorLevelsOrder), ReflectionExtensions.GetPropertyDisplayName <GraphicalAnalysisModel>(i => i.SecondCatFactor))) { return(ValidationInfo); } if (gaVariables.HistogramSelected && (gaVariables.XAxisMin.HasValue || gaVariables.XAxisMax.HasValue)) { ValidationInfo.AddWarningMessage("For the histogram plot the axis ranges cannot be changed."); } if (gaVariables.BoxplotSelected && (gaVariables.XAxisMin.HasValue || gaVariables.XAxisMax.HasValue)) { ValidationInfo.AddWarningMessage("For the boxplot the X-axis range cannot be changed."); } if (gaVariables.CaseProfilesPlotSelected && !xIsNumeric && (gaVariables.XAxisMin.HasValue || gaVariables.XAxisMax.HasValue)) { ValidationInfo.AddWarningMessage("On the case profiles plot, as the X-axis variable is categorical the X-axis range cannot be changed."); } if (gaVariables.ErrorBarPlotSelected && (gaVariables.XAxisMin.HasValue || gaVariables.XAxisMax.HasValue)) { ValidationInfo.AddWarningMessage("For the Means with error bars plot the X-axis range cannot be changed."); } if (gaVariables.ScatterplotSelected && !yIsNumeric && (gaVariables.YAxisMin.HasValue || gaVariables.YAxisMax.HasValue)) { ValidationInfo.AddWarningMessage("On the scatterplot, as the Y-axis variable is categorical the Y-axis range cannot be changed."); } if (gaVariables.ScatterplotSelected && !xIsNumeric && (gaVariables.XAxisMin.HasValue || gaVariables.XAxisMax.HasValue)) { ValidationInfo.AddWarningMessage("On the scatterplot, as the X-axis variable is categorical the X-axis range cannot be changed."); } if (gaVariables.XAxisMin.HasValue != gaVariables.XAxisMax.HasValue) { ValidationInfo.AddErrorMessage("You have only defined one of the values for the X-axis range - both are required to generate the plot."); return(ValidationInfo); } if (gaVariables.YAxisMin.HasValue != gaVariables.YAxisMax.HasValue) { ValidationInfo.AddErrorMessage("You have only defined one of the values for the Y-axis range - both are required to generate the plot."); return(ValidationInfo); } if (gaVariables.XAxisMin >= gaVariables.XAxisMax) { ValidationInfo.AddErrorMessage("For the X-axis range, the minimum value needs to be less than the maximum."); return(ValidationInfo); } if (gaVariables.YAxisMin >= gaVariables.YAxisMax) { ValidationInfo.AddErrorMessage("For the Y-axis range, the minimum value needs to be less than the maximum."); return(ValidationInfo); } //if get here then no errors so return true return(ValidationInfo); }
public override ValidationInfo Validate() { //go through all the column names, if any are not numeric then stop the analysis List <string> allVars = new List <string>(); allVars.AddRange(maVariables.Responses); if (maVariables.CategoricalPredictor != null) { allVars.Add(maVariables.CategoricalPredictor); } if (maVariables.ContinuousPredictors != null) { allVars.AddRange(maVariables.ContinuousPredictors); } allVars.Add(maVariables.CaseID); if (!CheckColumnNames(allVars)) { return(ValidationInfo); } if (maVariables.CategoricalPredictor != null) { if (!CheckFactorsHaveLevels(maVariables.CategoricalPredictor, true)) { return(ValidationInfo); } if (CountDistinctLevels(maVariables.CategoricalPredictor) < 2) { ValidationInfo.AddErrorMessage("At least one of your categorical predictors only has one level. Please remove it from the analysis."); return(ValidationInfo); } } //Go through each response foreach (string response in maVariables.Responses) { if (!CheckIsNumeric(response)) { ValidationInfo.AddErrorMessage("The Response (" + response + ") contains non-numeric data that cannot be processed. Please check the data and make sure it was entered correctly."); return(ValidationInfo); } CheckTransformations(maVariables.ResponseTransformation, response); //Do checks to ensure that treatments contain a response etc and the responses contain a treatment etc... if (maVariables.CategoricalPredictor != null && maVariables.AnalysisType == MultivariateAnalysisModel.AnalysisOption.LinearDiscriminantAnalysis) { //check response and cat factors contain values if (!CheckFactorAndResponseNotBlank(maVariables.CategoricalPredictor, response, ReflectionExtensions.GetPropertyDisplayName <MultivariateAnalysisModel>(i => i.CategoricalPredictor))) { return(ValidationInfo); } if (!CheckResponsesPerLevel(maVariables.CategoricalPredictor, response, ReflectionExtensions.GetPropertyDisplayName <MultivariateAnalysisModel>(i => i.CategoricalPredictor))) { return(ValidationInfo); } } //Go through each continuous predictor if (maVariables.ContinuousPredictors != null && maVariables.AnalysisType == MultivariateAnalysisModel.AnalysisOption.PartialLeastSquares) { foreach (string continuousPredictor in maVariables.ContinuousPredictors) { if (!CheckIsNumeric(continuousPredictor)) { ValidationInfo.AddErrorMessage("The continuous predictor (" + continuousPredictor + ") contains non-numeric data that cannot be processed. Please check the data and make sure it was entered correctly."); return(ValidationInfo); } else if (!CheckFactorAndResponseNotBlank(continuousPredictor, response, ReflectionExtensions.GetPropertyDisplayName <MultivariateAnalysisModel>(i => i.ContinuousPredictors))) { return(ValidationInfo); } } } //check response and cat factors contain values if (maVariables.CaseID != null && !CheckFactorAndResponseNotBlank(maVariables.CaseID, response, ReflectionExtensions.GetPropertyDisplayName <MultivariateAnalysisModel>(i => i.CaseID))) { return(ValidationInfo); } } //check that all the responses contain the same number of responses, row by row int expectedResponses = maVariables.Responses.Count(); foreach (DataRow row in DataTable.Rows) { int actualResponses = 0; foreach (string response in maVariables.Responses) { if (!String.IsNullOrEmpty(row[response].ToString())) { actualResponses++; } } if (expectedResponses != actualResponses) { ValidationInfo.AddErrorMessage("One or more of the response variables contains missing data. Please delete any rows of the dataset that contain missing data prior to running the analysis."); return(ValidationInfo); } } if (maVariables.AnalysisType == MultivariateAnalysisModel.AnalysisOption.PrincipalComponentsAnalysis) { if (maVariables.CategoricalPredictor != null) { ValidationInfo.AddWarningMessage("When performing a PCA analysis the categorical predictor you have selected will not be used. If you do need to use them in the analysis, then another analysis option may be more appropriate."); } else if (maVariables.ContinuousPredictors != null) { ValidationInfo.AddWarningMessage("When performing a PCA analysis the continuous predictors you have selected will not be used. If you do need to use them in the analysis, then another analysis option may be more appropriate."); } } else if (maVariables.AnalysisType == MultivariateAnalysisModel.AnalysisOption.ClusterAnalysis) { if (maVariables.CategoricalPredictor != null) { ValidationInfo.AddWarningMessage("When performing a Cluster analysis the categorical predictor you have selected will not be used. If you do need to use them in the analysis, then another analysis option may be more appropriate."); } if (maVariables.ContinuousPredictors != null) { ValidationInfo.AddWarningMessage("When performing a Cluster analysis the continuous predictors you have selected will not be used. If you do need to use them in the analysis, then another analysis option may be more appropriate."); } } else if (maVariables.AnalysisType == MultivariateAnalysisModel.AnalysisOption.LinearDiscriminantAnalysis) { if (maVariables.CategoricalPredictor == null) { ValidationInfo.AddErrorMessage("When performing a LDA analysis a categorical predictor is required."); } if (maVariables.ContinuousPredictors != null) { ValidationInfo.AddWarningMessage("When performing a LDA analysis the continuous predictors you have selected will not be used. If you do need to use them in the analysis, then another analysis option may be more appropriate."); } } //display the warning messages (if any) and return the result return(ValidationInfo); }
public override ValidationInfo Validate() { //go through all the column names, if any are numeric then stop the analysis List <string> allVars = new List <string>(); allVars.AddVariables(etVariables.Treatments); allVars.AddVariables(etVariables.OtherDesignFactors); allVars.Add(etVariables.Response); allVars.AddVariables(etVariables.Covariates); if (!CheckColumnNames(allVars)) { return(ValidationInfo); } //First create a list of catogorical variables selected (i.e. as treatments and other factors) List <string> categorical = new List <string>(); categorical.AddVariables(etVariables.Treatments); categorical.AddVariables(etVariables.OtherDesignFactors); //check that the factors have at least 2 levels if (!CheckFactorsHaveLevels(categorical, true)) { return(ValidationInfo); } //Do checks to ensure that treatments contain a response etc and the responses contain a treatment etc... if (!CheckResponsesPerLevel(etVariables.Treatments, etVariables.Response, ReflectionExtensions.GetPropertyDisplayName <EquivalenceTOSTTestModel>(i => i.Treatments))) { return(ValidationInfo); } if (!CheckResponsesPerLevel(etVariables.OtherDesignFactors, etVariables.Response, ReflectionExtensions.GetPropertyDisplayName <EquivalenceTOSTTestModel>(i => i.OtherDesignFactors))) { return(ValidationInfo); } //do data checks on the treatments/other factors and response if (!CategoricalAgainstContinuousVariableChecks(categorical, etVariables.Response)) { return(ValidationInfo); } //check transformations if (etVariables.EquivalenceBoundsType == EquivalenceTOSTTestModel.EquivalenceBoundsOption.Percentage && etVariables.ComparisonType == EquivalenceTOSTTestModel.ComparisonOption.AllPairwise && etVariables.ResponseTransformation == "None") { ValidationInfo.AddWarningMessage("As you have chosen the % equivalence bounds, the actual boundaries has been calculated as a % of the overall mean of the response."); } else if (etVariables.EquivalenceBoundsType == EquivalenceTOSTTestModel.EquivalenceBoundsOption.Percentage && etVariables.ComparisonType == EquivalenceTOSTTestModel.ComparisonOption.ComparisonsToControl && etVariables.ResponseTransformation == "None") { ValidationInfo.AddWarningMessage("As you have chosen the % equivalence bounds, the actual boundaries has been calculated as a % of the selected control group."); } else if (etVariables.EquivalenceBoundsType == EquivalenceTOSTTestModel.EquivalenceBoundsOption.Absolute && etVariables.ResponseTransformation.StartsWith("Log")) { ValidationInfo.AddErrorMessage("As you have chosen to log transformed the response, the comparisons between the predicted means will be in the form of ratios. This implies that the difference between the means will be a % change and hence you should select % boundaries rather than absolute boundaries."); return(ValidationInfo); } else if (etVariables.EquivalenceBoundsType == EquivalenceTOSTTestModel.EquivalenceBoundsOption.Percentage && !etVariables.ResponseTransformation.StartsWith("Log")) { ValidationInfo.AddErrorMessage("As you have selected to [sqrt, arcsine, rank] transform the responses you should choose absolute boundaries rather than % boundaries. The absolute boundaries should be defined on the transformed scale rather than the original scale."); return(ValidationInfo); } CheckTransformations(etVariables.ResponseTransformation, etVariables.Response); if (etVariables.Covariates != null) { CheckTransformations(etVariables.CovariateTransformation, etVariables.Covariates, true); } //do data checks on the treatments/other factors and covariate (if selected) if (etVariables.Covariates != null) { foreach (string covariate in etVariables.Covariates) { if (!CategoricalAgainstContinuousVariableChecks(categorical, covariate)) { return(ValidationInfo); } } } if (etVariables.Covariates != null && String.IsNullOrEmpty(etVariables.PrimaryFactor)) { ValidationInfo.AddErrorMessage("You have selected a covariate but no primary factor is selected."); } if (etVariables.ComparisonType == EquivalenceTOSTTestModel.ComparisonOption.ComparisonsToControl && etVariables.Treatments.Count() > 1) { ValidationInfo.AddErrorMessage("You have selected to compare back to a control but this is not possible with multiple treatments."); } else if (etVariables.ComparisonType == EquivalenceTOSTTestModel.ComparisonOption.ComparisonsToControl && String.IsNullOrEmpty(etVariables.ControlGroup)) { ValidationInfo.AddErrorMessage("You have selected to compare back to a control but no control group is selected."); } if (etVariables.LowerBoundAbsolute > etVariables.UpperBoundAbsolute) { ValidationInfo.AddErrorMessage("The lower bound selected is higher than the upper bound, please check the bounds as the lower bound should be less than the upper bound."); } if (etVariables.EquivalenceBoundsType == EquivalenceTOSTTestModel.EquivalenceBoundsOption.Absolute && (etVariables.LowerBoundAbsolute.HasValue == false && etVariables.UpperBoundAbsolute.HasValue == false)) { ValidationInfo.AddErrorMessage("Absolute selected but bounds not entered."); } else if (etVariables.EquivalenceBoundsType == EquivalenceTOSTTestModel.EquivalenceBoundsOption.Percentage && (etVariables.LowerBoundPercentageChange.HasValue == false && etVariables.UpperBoundPercentageChange.HasValue == false)) { ValidationInfo.AddErrorMessage("Percentage equivelence bounds selected but no bounds entered."); } //if get here then no errors so return true return(ValidationInfo); }