Как: при циклическом действии поддерживать соответствие данных внешним изменениям - PullRequest
0 голосов
/ 02 июня 2019

Короче говоря, я в основном создаю симулятор планировщика процессов. Как уже говорят теги, я использую React + Redux + ImmutableJS. Прежде всего позвольте мне признать, что у меня нет большого опыта работы с этими инструментами, поскольку я использую их в этом проекте для изучения.

К проблеме: Один из алгоритмов планирования процессов, которые я моделирую, - это «Кратчайшее задание - первое» (SJF), его действие называется:

SJF Action - находится в файле Actions.js https://jsfiddle.net/p7rs93kf/

export const algorithmSJF = (coreList, processList, finishedProcessList, isFirst) => (dispatch) => {
if (isFirst) {
    let sortedProcessList = sortList(processList, 'totalExecutionTime')
    processList = sortedProcessList
}
setTimeout(() => {
    let availableCores = getAvailableCoreAmmount(coreList)

    //Keep running until empty process list
    if (processList) {

        // Allocating Process to Cores
        for (let i = 0; i < coreList.length; i++) {
            if(coreList[i].status === 'waiting for process' && availableCores > 0) {
                for (let j = 0; j < processList.length; j++) {
                    if(processList[j].status === 'ready') {
                        let freeProcessId = processList[j].id
                        processList[j].status = 'executing'
                        if(freeProcessId >= 0) {
                            coreList[i].processInExecution = 'P' + freeProcessId
                            coreList[i].status = 'executing'
                            coreList[i].processInExecutionRemainingTime = processList[j].remainingExecutionTime
                            availableCores--
                        } else {
                            coreList[i].processInExecution = 'none'
                            coreList[i].status = 'waiting for process'
                            coreList[i].processInExecutionRemainingTime = -1
                            availableCores++
                        }
                        break
                    } 
                }
            }
        }
        dispatch(updateCoreProcessLists({coreList, processList, finishedProcessList}))

        //Remove 0 Remaining Time Process
        for (let i = 0; i < coreList.length; i++) {
                let runningProcessId = coreList[i].processInExecution.substring(1)
                if (runningProcessId !== 'none'.substring(1)) {
                    let currentProcess = processList.find(process => process.id.toString() === runningProcessId)
                    if(currentProcess.remainingExecutionTime === 0) {
                        coreList[i].processInExecution = 'none'
                        coreList[i].status = 'waiting for process'
                        coreList[i].processInExecutionRemainingTime = -1
                        availableCores++
                    }
                }
            }

        let currentFinishedProcesses = processList.filter(function(process) {
            return process.remainingExecutionTime === 0
        })
        currentFinishedProcesses = currentFinishedProcesses.map(function(process){
            process.status = 'finished'
            return process
        })

        Array.prototype.push.apply(finishedProcessList, currentFinishedProcesses)

        processList = processList.filter(function(process) {
            return process.remainingExecutionTime > 0
        })

        dispatch(updateCoreProcessLists({coreList, processList, finishedProcessList}))

        // Updates Executing Processes
        for (let i = 0; i < coreList.length; i++) {
            if(coreList[i].status === 'executing') {
                coreList[i].processInExecutionRemainingTime--
            }
        }
        for (let i = 0; i < processList.length; i++) {
            if(processList[i].status === 'executing') {
                processList[i].remainingExecutionTime--
            }
        }

        dispatch(updateCoreProcessLists({coreList, processList, finishedProcessList}))

        dispatch(algorithmSJF(coreList, processList, finishedProcessList, false))
    } else {
        setTimeout(() => {
            this.props.history.push('/')
        }, 10000)
    }
}, 1000)

}

Добавить случайный процесс ФУНКЦИЯ - Находится внутри компонента планировщика https://jsfiddle.net/3uL5r9av/

let totalExecutionTime = randomIntFromInterval(4, 20)
let priority = randomIntFromInterval(0, 3)
let bytesToExecute = randomIntFromInterval(32, 1024)
let processList = this.state.processList
let id = Math.max.apply(Math, 
         this.state.processList.map(function(process) { return 
         process.id; }))
let newProcess = {name: "P"+(id+1), id: id + 1, status: 'ready', 
                 totalExecutionTime: totalExecutionTime, 
                 remainingExecutionTime: 
                 totalExecutionTime, priority: priority, inserted: true, 
                 bytes: bytesToExecute}

 processList = [...this.state.processList, newProcess]

 if (this.state.algorithm === 'sjf') {
     processList = sortList(processList, 'totalExecutionTime')
 }

 //ISSUE HERE
 this.props.updateProcessList({processList})
 this.setState({
    processList
 })

В пользовательском меню, пока все работает, у меня есть кнопка, которая добавляет в список «процессов» случайный процесс. Проблема здесь в том, что функция добавления нового процесса в список обновляет список (и даже новый элемент появляется в представлении), но когда он возвращается к действию SJF и вызывает его диспетчеризацию, processList не обновляется. Я понимаю, что речь идет о факте "самозвонка" и использовании "локальной" переменной processList, но есть какие-нибудь идеи о том, как решить эту проблему или правильно ее организовать?

Пожалуйста, не стесняйтесь спрашивать дополнительную информацию, я с удовольствием отредактирую вопрос. Заранее спасибо

...