source: trunk/autoquest-core-usability/src/main/java/de/ugoe/cs/autoquest/usability/RequiredInefficientActionsRule.java @ 1493

Last change on this file since 1493 was 1493, checked in by pharms, 10 years ago
  • state of the HCSE 2014 Paper. An appropriate tag will follow.
File size: 5.5 KB
Line 
1//   Copyright 2012 Georg-August-Universität Göttingen, Germany
2//
3//   Licensed under the Apache License, Version 2.0 (the "License");
4//   you may not use this file except in compliance with the License.
5//   You may obtain a copy of the License at
6//
7//       http://www.apache.org/licenses/LICENSE-2.0
8//
9//   Unless required by applicable law or agreed to in writing, software
10//   distributed under the License is distributed on an "AS IS" BASIS,
11//   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12//   See the License for the specific language governing permissions and
13//   limitations under the License.
14
15package de.ugoe.cs.autoquest.usability;
16
17import java.util.Collection;
18import java.util.HashMap;
19import java.util.Map;
20
21import org.apache.commons.math3.stat.descriptive.DescriptiveStatistics;
22
23import de.ugoe.cs.autoquest.eventcore.Event;
24import de.ugoe.cs.autoquest.eventcore.gui.Scroll;
25import de.ugoe.cs.autoquest.tasktrees.treeifc.DefaultTaskInstanceTraversingVisitor;
26import de.ugoe.cs.autoquest.tasktrees.treeifc.IEventTask;
27import de.ugoe.cs.autoquest.tasktrees.treeifc.IEventTaskInstance;
28import de.ugoe.cs.autoquest.tasktrees.treeifc.IMarkingTemporalRelationship;
29import de.ugoe.cs.autoquest.tasktrees.treeifc.ITask;
30import de.ugoe.cs.autoquest.tasktrees.treeifc.ITaskInstance;
31import de.ugoe.cs.autoquest.tasktrees.treeifc.ITaskModel;
32
33/**
34 * TODO comment
35 *
36 * @version $Revision: $ $Date: 16.07.2012$
37 * @author 2012, last modified by $Author: pharms$
38 */
39public class RequiredInefficientActionsRule implements UsabilityEvaluationRule {
40
41    /*
42     * (non-Javadoc)
43     *
44     * @see de.ugoe.cs.usability.UsabilityEvaluationRule#evaluate(TaskTree)
45     */
46    @Override
47    public UsabilityEvaluationResult evaluate(ITaskModel taskModel) {
48        UsabilityEvaluationResult results = new UsabilityEvaluationResult(taskModel);
49
50        Map<ITask, double[]> smellingTasks = getInefficientActionStatistics(taskModel.getTasks());
51        analyzeTasksWithInefficientActions(smellingTasks, results, taskModel);
52
53        return results;
54    }
55
56    /**
57     *
58     */
59    private void analyzeTasksWithInefficientActions(Map<ITask, double[]>      smellingTasks,
60                                                    UsabilityEvaluationResult results,
61                                                    ITaskModel                taskModel)
62    {
63
64        for (Map.Entry<ITask, double[]> entry : smellingTasks.entrySet()) {
65            DescriptiveStatistics stats = new DescriptiveStatistics(entry.getValue());
66           
67            int ratio = (int) (1000 * stats.getMean());
68
69            UsabilityDefectSeverity severity = UsabilityDefectSeverity.getSeverity
70                (ratio, 500, 300, 200, 100, entry.getKey(), taskModel);
71
72            if (severity != null) {
73                Map<String, Object> parameters = new HashMap<String, Object>();
74                parameters.put("task", entry.getKey());
75                parameters.put("ratio", (ratio / 10));
76
77                results.addDefect
78                    (severity, UsabilityDefectDescription.INEFFICIENT_ACTIONS, parameters);
79            }
80        }
81    }
82
83    /**
84     *
85     */
86    private Map<ITask, double[]> getInefficientActionStatistics(Collection<ITask> tasks) {
87        Map<ITask, double[]> inefficientActionRatios = new HashMap<ITask, double[]>();
88       
89        for (ITask task : tasks) {
90            if (taskMustBeChecked(task))  {
91                double[] ratios = getRatiosOfInefficientActionsInInstances(task);
92               
93                for (int i = 0; i < ratios.length; i++) {
94                    if (ratios[i] > 0) {
95                        // there is at least on inefficient action
96                        inefficientActionRatios.put(task, ratios);
97                        break;
98                    }
99                }
100            }
101        }
102       
103        return inefficientActionRatios;
104    }
105
106    /**
107     *
108     */
109    private boolean taskMustBeChecked(ITask task) {
110        if ((task instanceof IEventTask) || (task instanceof IMarkingTemporalRelationship)) {
111            // event tasks are not considered
112            // marking temporal relationships have a child, that is more important, but it will
113            // be checked independently as all tasks of a task model are checked separately
114            return false;
115        }
116        else {
117            return true;
118        }
119    }
120
121    /**
122     *
123     */
124    private double[] getRatiosOfInefficientActionsInInstances(ITask task) {
125        Collection<ITaskInstance> instances = task.getInstances();
126       
127        double[] ratios = new double[instances.size()];
128        int index = 0;
129        for (ITaskInstance instance : instances) {
130            ratios[index++] = getRatioOfInefficientActionsInInstance(instance);
131        }
132       
133        return ratios;
134    }
135
136    /**
137     *
138     */
139    private double getRatioOfInefficientActionsInInstance(ITaskInstance instance) {
140        final int[] count = new int[2];
141        count[0] = 0;
142        count[1] = 0;
143       
144        instance.accept(new DefaultTaskInstanceTraversingVisitor() {
145            @Override
146            public void visit(IEventTaskInstance eventTaskInstance) {
147                if (isInefficientAction(eventTaskInstance.getEvent())) {
148                    count[0]++;
149                }
150               
151                count[1]++;
152            }
153           
154        });
155       
156        return (double) count[0] / count[1];
157    }
158
159    /**
160     *
161     */
162    private boolean isInefficientAction(Event event) {
163        return (event.getType() instanceof Scroll);
164    }
165
166}
Note: See TracBrowser for help on using the repository browser.