执行任务的 Xc8 位访问 以 C 方式读取或写入位字段使用结构定义位字段在循环内使用函数指针

问题描述

在 xc8 mplab 中,我有一个变量,例如 temp=0b10100100(8 位)我想根据 temp 位编写一个代码来执行任务 1 和任务 2 连续例如临时的第一位是 1 所以任务 1 应该是完成后第二个临时位为 0,所以任务 2 应该完成,依此类推到临时位结束 提前致谢

解决方法

据我了解您的问题,我有三种方法可以解决您的问题。

  1. 以 C 语言方式读取或写入位域。
  2. 使用结构定义位域。
  3. 在循环中使用函数指针来执行任务。

以 C 方式读取或写入位字段

使用 C 中的按位运算符,可以操作整数变量中的任何位。

#include <stdio.h>

#define BIT_READ(var,bitno)    (var & (1 << bitno))
#define BIT_RESET(var,bitno)   (var &= ~(1 << bitno))
#define BIT_SET(var,bitno)     (var |= 1 << bitno)

void Task1() {
    printf("Task1\n");
}

void Task2() {
    printf("Task2\n");
}

void Task3() {
    printf("Task3\n");
}

void Task4() {
    printf("Task4\n");
}

void Task5() {
    printf("Task5\n");
}

void Task6() {
    printf("Task6\n");
}

void Task7() {
    printf("Task7\n");
}

void Task8() {
    printf("Task8\n");
}

void main(void) {

    unsigned char temp;
    BIT_SET(temp,0);
    if(BIT_READ(temp,0)) {
        Task1();
        BIT_RESET(temp,0);
    }
    
    BIT_SET(temp,6);
    if(BIT_READ(temp,6)) {
        Task7();
        BIT_RESET(temp,6);
    }
    // You will see that only Task1 and Task7 will execute
}

使用结构定义位字段。

XC8 编译器支持定义为结构的位域。

#include <stdio.h>

union {
    struct {
        unsigned bit0   : 1;
        unsigned bit1   : 1;
        unsigned bit2   : 1;
        unsigned bit3   : 1;
        unsigned bit4   : 1;
        unsigned bit5   : 1;
        unsigned bit6   : 1;
        unsigned bit7   : 1;
    };
    unsigned char reg; // For register access
} temp;


void Task1() {
    printf("Task1\n");
}

void Task2() {
    printf("Task2\n");
}

void Task3() {
    printf("Task3\n");
}

void Task4() {
    printf("Task4\n");
}

void Task5() {
    printf("Task5\n");
}

void Task6() {
    printf("Task6\n");
}

void Task7() {
    printf("Task7\n");
}

void Task8() {
    printf("Task8\n");
}

void main(void) {
    temp.reg = 0b00101101;
    
    if(temp.bit0) {
        temp.bit0 = 0;
        // Do task1
        Task1();
    }
    if(temp.bit1) {
        temp.bit1 = 0;
        // Do task2
        Task2();
    }
    if(temp.bit2) {
        temp.bit2 = 0;
        // Do task3
        Task3();
    }
    if(temp.bit3) {
        temp.bit3 = 0;
        // Do task4
        Task4();
    }
    if(temp.bit4) {
        temp.bit4 = 0;
        // Do task5
        Task5();
    }
    if(temp.bit5) {
        temp.bit5 = 0;
        // Do task6
        Task6();
    }
    if(temp.bit6) {
        temp.bit6 = 0;
        // Do task7
        Task7();
    }
    if(temp.bit7) {
        temp.bit7 = 0;
        // Do task8
        Task8();
    }
    // In this case the tasks 1,3,4 and 6 will be executed.
}

在循环内使用函数指针

这种方法对代码大小有效,但对执行速度无效。

#include <stdio.h>

void Task1() {
    printf("Task1\n");
}

void Task2() {
    printf("Task2\n");
}

void Task3() {
    printf("Task3\n");
}

void Task4() {
    printf("Task4\n");
}

void Task5() {
    printf("Task5\n");
}

void Task6() {
    printf("Task6\n");
}

void Task7() {
    printf("Task7\n");
}

void Task8() {
    printf("Task8\n");
}

typedef void (*Task)(void);
Task tasks[] = {
    Task1,Task2,Task3,Task4,Task5,Task6,Task7,Task8
};

void main(void) {
    unsigned char temp;
    temp = 0b11001010;
    
    // Or alternatively using function pointer:
    unsigned char mask = 1;
    for(char i = 0; i < sizeof(tasks); i++) {
        if((temp.reg & mask)) {
            // Check the temp's bits from 0 to 7 and call the related task 
            // accordingly. Better check bounds in order to prevent PC 
            // overflow,hence device reset.
            if(i >= sizeof(tasks)) break;
            temp.reg &= ~mask; // Clear the bit so that the task does not 
                               // execute repeatedly
            if(temp.reg & mask) {
                printf("bit %d not cleared\n",i);
            }
            else {
                printf("bit %d cleared\n",i);
            }
            tasks[i](); // Execute the related task
        }
        mask <<= 1; // Mask the next bit toward 7th bit.
    }
}

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...