I2C读取数据的有关问题

I2C读取数据的问题
C/C++ code

uchar Read_Byte()
{
    uchar i, j, mesg;
        scl = 0;/*拉低scl*/
    delay();
    sda = 1;/*释放sda*/
    delay();
    for (i = 0; i < 8; i++)
    {
        scl = 1;
        delay();
        j = sda;
        mesg = (mesg << 1) | j;
        scl = 0;
        delay();
    }
    return mesg;
}

在循环之前,一定要把scl拉低,然后释放scl吗???scl拉低从机可以往sda写数据,那sda为什么要释放的话,当scl拉低时,sda的数据不是可以改变的吗??sda释不释放不是无所谓吗??敬请大家帮我解惑,非常感谢。

------解决方案--------------------
scl = 0;/*拉低scl*/
delay();
sda = 1;/*释放sda*/
可以这样理解:拉低SCL等待对方输出SDA,自己这边释放SDA。
原因在于,在进行本函数操作之前,自己这边可能输出过SDA=0,不释放,相与的结果必定为0,于是收不到对方的SDA数据了。
不同的人写出来的程序由所区别,但是从写切换成读。释放(SDA=1)都是必须的。
------解决方案--------------------
这个主要看你用的单片机或MCU的IO引脚的属性,以及你配置的IO口属性,比如某些51单片机(如STC的51单片机),如果将引脚设置为双向口,接收时必须先将SDA引脚置高,否则如果前面的操作将这个引脚置低的话,无论对面的芯片将这个引脚置1置0,从单片机中读到SDA引脚的数据都是0.SDA=1就相当于将IO口置于弱上拉输入状态,这样外面输入高就是高,输入低就是低。SDA=0时,相当于内部将引脚接地了,因此对方输出高电平时也无法将电平拉起来了。